# Nullable Expressions

All Elements languages allow the use of Nullable Types in standard Arithmetic and Logical Expressions and will automatically propagate nullability to their result type. So if one element of an expression is nullable, that information will bubble up through the expression tree and the result will be nullable, too.

When using the Swift language, nullables need to be of the implicitly wrapped type (i.e.declared with `!`) to be used directly, or they can be unwrapped inline with `?`.

Consider the following example:

``````var x: Int32 := 5;
var y: nullable Int32 := 10;
var z: nullable Int32;

var a := x + y + z;
``````
``````Int32 x = 5;
Int32? y = 10;
Int32? z;

var a = x + y + z;
``````
``````let x: Int32 = 5
let y: Int32! = 10
let z: Int32?

let a = x + y + z?;
``````
``````Int32 x = 5;
Int32? y = 10;
Int32? z;

var a = x + y + z;
``````
``````Dim x As Int32 = 5
Dum y As Int32? = 10
Dum z As Int32?

Dim a = x + y * z;
``````

Both `y` and `z` are of nullable type. That means that the subexpression `x + y` will be promoted to be an nullable `Int32` as well, it's value will be `15`. Next, this value is then added to `z`, which is not only potentially nullable but in fact `nil`. Regardless of `z`’s value, the end result will be a nullable type again, and because `z` is `nil`, the end result, `15 + nil`, is `nil`.

So this code declares `a` as a nullable `Int32` (solely based on the input types of the expression) and at runtime `a` will evaluate to `nil` (because one on ifs inlut vaklues was `nil`)

## Determining the Type of a Nullable Expression

To determine the type of an expression, the following rules are applied:

1. Initially, the nullability characteristic of the operands is ignored, determining the result base type in the usual way.
2. If any one of the operands is nullable, the result type will be nullable as well.

Consider the following example:

``````var x: Int32 := 5;
var y: nullable Double := 5.0;

var a := x + y; // 10, a will be a nullable Single
``````

In step one, the base types of `x` and `y` (`Int32` and `Double`) are considered to determine that the resulting expression will also be of type `Double`. Then, because one of the parameters (`z`) is nullable, the entire result is promoted to a `nullable Double`.

## Equality of Nullable Types

The above applies to all operators with only a single important exception: equality comparisons (`=` and `≠` / `<>` / `!=`) always result in a not-nullable Boolean to preserve the established logic of comparing reference-based values. (Other comparison operators, i.e. `<`, `≤` `>` and `≥`, will produce a nullable boolean as result if one of the operands is nullable, according to the above rules.)

For Example:

``````var x: Int32 := 5;
var y: nullable Int32 := 5;
var z: nullable Int32;

var a := x = y; // true, a will be a regular Boolean
var b := x = z; // false, b will be a regular Boolean
``````

## Determining the Result of a Nullable Expression

When evaluating expressions at runtime, the result will be `nil`, if one or both of the operands is `nil`; otherwise the result is the determined just as it would be for non-nullable expressions by applying the operator(s) to the respective values. It is worth noting that a single `nil` in a complex or nested expression will "bubble up" and turn the entire expression `nil`.

Examples (assuming the right-hand operator is a nullable Int32 type):

``````var x: Int32 := 5;
var y: nullable Int32 := 10;
var z: nullable Int32;

var a := x + z; // = nil
var b := x + y; // = 15;
var b := (x + z) * y; // = nil;
``````
• The above rules are specific to nullable types, but do not necessarily apply to custom class based types that implement their own operators. For example, the `+` concatenation operator on Strings will preserve the original string when appending a `nil` string via `+`.
• `if`, `while` and `until` statements will accept nullable booleans, and treat `nil` as `false`.

## Result Tables

The following tables provide a matrix for how `nil` and Boolean values interact.

### Equality

The following rules apply to the equality (`=` and `≠`/`<>`/`!=`) operators:

• nil = nil => `true`
• nil = non-nil => `false`
• non-nil = nil => `false`
• non-nil = non-nil => compare value

### Non-Equality

• nil ≠ nil => `false`
• nil ≠ non-nil => `true`
• non-nil ≠ nil => `true`
• non-nil ≠ non-nil => actual values are compared

## Booleans

### Truth table for the `not` / `!` boolean operator

• (not `true`) => `false`
• (not `false`) => `true`
• (not `nil`) => `nil`

### Truth table for the `and` / `&&` boolean operator

• `true` and `true` => `true`
• `true` and `false` => `false`
• `true` and `nil` => `nil`
• `false` and `true` => `false` — via Boolean Short-Circuit
• `false` and `false` => `false` — via Boolean Short-Circuit
• `false` and `nil` => `false` — via Boolean Short-Circuit
• `nil` and `true` => `nil`
• `nil` and `false` => `false`
• `nil` and `nil` => `nil`

### Truth table for the `or` / `||` boolean operator

• `true` or `true` => `true` — via Boolean Short-Circuit
• `true` or `false` => `true` — via [Boolean Short-Circuit
• `true` or `nil` => `true` — via [Boolean Short-Circuit
• `false` or `true` => `true`
• `false` or `false` => `false`
• `false` or `nil` => `nil`
• `nil` or `true` => `true`
• `nil` or `false` => `nil`
• `nil` or `nil` => `nil`

### Truth table for the `xor` / `^` boolean operator

• `true` xor `true` => `false`
• `true` xor `false` => `true`
• `true` xor `nil` => `nil`
• `false` xor `true` => `true`
• `false` xor `false` => `false`
• `false` xor `nil` => `nil`
• `nil` xor `true` => `nil` — via Boolean Short-Circuit
• `nil` xor `false` => `nil` — via Boolean Short-Circuit
• `nil` xor `nil` => `nil` — via Boolean Short-Circuit

Note: There is no XOR operator in SQL, which is where the nullable truth tables are based on, however, "A xor B" can be expressed as "not (A and B) and (A or B)" and the above truth table derived from that.

### Truth table for the Oxygene `implies` boolean operator

• `true` implies `true` => `true`
• `true` implies `false` => `false`
• `true` implies `nil` => `nil`
• `false` implies `true` => `true` — via Boolean Short-Circuit
• `false` implies `false` => `true` — via Boolean Short-Circuit
• `false` implies `nil` => `true` — via Boolean Short-Circuit
• `nil` implies `true` => `nil`
• `nil` implies `false` => `nil`
• `nil` implies `nil` => `nil`

### Boolean Short-Circuit

Boolean Short-Circuit evaluation is possible for the following operators if the left operand has a specific value:

• `and`/`&&`: `false` => `false`

• `or`/`||`: `true` => `true`

• `xor`/`^`: `nil` => `nil`

(Note that `xor`/`^` does not ever short-circuit for non-nullable expressions.)