# Parameter Conditionals

Standard (unconditional) parameter expansion turns the syntaxes `$variable` and `${variable}` into their respective contents. Conditional parameter expansion uses an operator following the variable name (inside braces) to indicate conditional expansion.

The condition for expansion depends on the operator used.

| Name                 | Condition        | Operator | Example             |
| -------------------- | ---------------- | -------- | ------------------- |
| Assign default value | unset            | `=`      | `${var=default}`    |
| Assign default value | unset or NULL    | `:=`     | `${var:=default}`   |
| Use default value    | unset            | `-`      | `${var-default}`    |
| Use default value    | unset or NULL    | `:-`     | `${var:-default}`   |
| Use alternate value  | set              | `+`      | `${var+alternate}`  |
| Use alternate value  | set and non-NULL | `:+`     | `${var:+alternate}` |

Combining the syntax for assigning default values (`${var=default` and `${var:=default}`) with a shell built-in such as `:` allows you to assign default values to one or more variables. Since the : built-in meets these requirements:

* Does not process any arguments given
* Performs no action and returns immediately
* Is a built-in and as-such returns quickly

The shell built-ins `true` and `false` also meet the criteria, but `false` has an undesirable affect on exit status and `true`, while identical in functionality to `:`, is not guaranteed to adhere to that criterion.

If the syntax for conditionally assigning a default value has modified the contents of the variable, the assignment is done before the final expansion, meaning that the provided default value is expanded.

```
1 #!/bin/sh
2 : ${foo=bar} ${bar:=baz}
3 echo foo = "$foo"
4 echo bar = "$bar"
```

If `foo` and `bar` are both unset when the above code runs:

```
foo = bar
bar = baz
```

If `foo=abc` and `bar=123` when the code runs:

```
foo = abc
bar = 123
```

If `foo` and `bar` are both set but empty (NULL):

```
foo = 
bar = baz
```

When both are set but empty, `foo` remains empty because the `=` operator (assign default value if unset) was used while `bar` gets set to the default value because the `:=` operator (assign default value if NULL or unset) was used.

Visually, it can be difficult to discern parameter expansion operators apart from each other. This can lead to the accidental removal of an expansion containing an default assignment. To avoid this danger, it is best to declare default assignments at the top of your code or start of a code block using the `:` built-in or similar.

After interpolation but before execution, a command such as `: ${foo=bar} ${bar:=baz}` may be translated into `: bar baz` which upon execution will give the arguments `bar` and `baz` to the `:` command. Hence why it is important to use a built-in such as : that ignores any arguments given.
