# Spreadsheet Expressions
Spreadsheet expressions are an optional feature not enabled in the default parser configurations. To enable it, include [`spreadsheet.js`](js/spreadsheet.js) / [`spreadsheet.php`](php/spreadsheet.php) and create a `Markdown` instance with a `new MDSpreadsheetReader()` included in its reader array.
## Expressions
As with many spreadsheet applications, a cell that begins with `=` is treated as a formula.
## Cell References
Values in other cells can be referenced with addresses. It consists of a column letter and an optional row number. When the row number is omitted the row is assumed to be the same as where the expression is located.
Only body rows of a table are included in calculations and can be referenced. Header rows are entirely ignored.
| Address | Description |
| -- | -- |
| `=A1` | Value from the leftmost column on the first row |
| `=C2` | Value from the third column from the left on the second row |
| `=A` | Value from the leftmost column on the same row as the expression |
| `=AB1` | Value from the 28th column from the left. Letters proceed A to Z for columns 1 to 26, then AA, AB, AC... for 27, 28, 29.... Limited to 2 letters (676 columns), which is way more than could ever reasonably fit in a markdown table. |
Rows or column references can be fixed for autofilled formulas (discussed below) by using a `$` before the column letters or row number.
| Address | Description |
| -- | -- |
| `=$A1` | First column and row. If transposed, the row may change but the column will not. |
| `=A$1` | First column and row. If transposed, the column may change but the row will not. |
| `=$A$1` | First column and row even if transposed. |
## Cell Ranges
Some functions accept a range of values which can be referenced with an address range. This consists of two addresses joined with a colon (`:`) and will include all the cells in the rectangle between them.
Examples.
| Range | Description |
| -- | -- |
| `A1:C9` | All the cells in columns A, B, and C from rows 1 through 9, inclusive. |
| `A:C` | All the cells in columns A, B, and C from all rows. |
Cell ranges can be used in functions like `SUM`, `AVERAGE`, `MAX`, and others that operate on arbitrary numbers of values.
If the cell range exceeds the number of rows or columns in a table, the out-of-bounds addresses will be skipped.
Omitting the row number is a low maintenance way of referring to all the cells in a column without having to update the lower bound as rows are added.
If a cell has a formula with a range that includes its own cell, the interpeter will automatically exclude it. E.g. this is valid:
```markdown
| Name | Qty |
| ----- | --------- |
| A | 2 |
| B | 3 |
| C | 1 |
| TOTAL | =SUM(B:B) |
```
The sum references column B and is also in column B but will not cause a circular reference. It will produce a result of 6.
## Operators
| Operator | Description |
| -- | -- |
| _x_ `+` _y_ | Addition |
| _x_ `-` _y_ | Subtraction |
| _x_ `*` _y_ | Multiplication |
| _x_ `/` _y_ | Division |
| `-`_x_ | Unary minus. Negates an argument. |
| _x_ `&` _y_ | Concatenate. Produces a text value. |
| _x_ `<` _y_ | Less than. Produces a Boolean value. |
| _x_ `<=` _y_ | Less than or equal. Produces a Boolean value. |
| _x_ `>` _y_ | Greater than. Produces a Boolean value. |
| _x_ `>=` _y_ | Greater than or equal. Produces a Boolean value. |
| _x_ `==` _y_ | Equal. Produces a Boolean value. |
| _x_ `!=` _y_ | Not equal. Produces a Boolean value. |
| `!`_x_ | Logical not. Produces a Boolean value. |
## Parentheses
Calculations can be grouped in parentheses to affect evaluation order.
| Example | Evaluation order |
| -- | -- |
| `=3*4+1*2` | 1. `=12+1*2` (multiply 3 and 4)
2. `=12+2` (multiply 1 and 2)
3. `=14` (add 12 and 2) |
| `=3*(4+1)*2` | 1. `=3*5*2` (add 4 and 1)
2. `=15*2` (multiply 3 and 5)
3. `=30` (multiply 15 and 2) |
## Functions
| Function | Description |
| -- | -- |
| `ABS(`_x_`)` | Absolute value |
| `AND(`_x_`,` _y_`,` ... `,` _z_`)` | Boolean AND of 1 or more arguments |
| `AVERAGE(`_x_`,` _y_`,` ... `,` _z_`)` | Statistical mean of 1 or more arguments. Non-numeric values are ignored. |
| `CEILING(`_x_`)` | Rounds a value up |
| `EXP(`_x_`)` | Raises _e_ to the power of _x_ |
| `FLOOR(`_x_`)` | Rounds a value down |
| `IF(`_test_`,` _trueval_`,` _falseval_`)` | Returns _trueval_ if _test_ evaluates to `TRUE`, otherwise returns _falseval_.
| `IFS(`_test1_`,` _val1_`,` _test2_`,` _val2_`,` ... `,` _fallbackval_`)` | Performs multiple if tests. If _test1_ is `TRUE`, returns _val1_. If _test2_ is `TRUE`, returns _val2_. Etc. If no tests are `TRUE`, the final _fallbackval_ is returned. Takes an odd number of arguments of 3 or more. |
| `ISBLANK(`_x_`)` | True if the value or cell is blank |
| `LN(`_x_`)` | Natural logarithm |
| `LOG(`_x_`,[` _base_`])` | Logarithm with a given _base_, or 10 if _base_ omitted |
| `LOWER(`_x_`)` | Lowercase of a text value |
| `MAX(`_x_`,` _y_`,` ... `,` _z_`)` | Maximum of 1 or more values |
| `MIN(`_x_`,` _y_`,` ... `,` _z_`)` | Minimum of 1 or more values |
| `MOD(`_x_`,` _y_`)` | Modulo division |
| `NOT(`_x_`)` | Boolean NOT |
| `OR(`_x_`,` _y_`,` ... `,` _z_`)` | Boolean OR of 1 or more arguments |
| `POWER(`_x_`,` _y_`)` | Raises _x_ to the _y_ exponent |
| `ROUND(`_x_`, [`_digits_`])` | Rounds a number to the nearest integer. If _digits_ is provided, rounds to that number of digits after the decimal place. Negative _digits_ will round to the nearest 10, 100, etc. |
| `SQRT(`_x_`)` | Square root |
| `SUBSTITUTE(`_text_`,` _pattern_`,` _replacement_`)` | Replaces all occurrences of _pattern_ in _text_ with _replacement_ |
| `SUM(`_x_`,` _y_`,` ... `,` _z_`)` | Sum of 1 or more numeric arguments. Non-numeric values are ignored. |
| `UPPER(`_x_`)` | Upercase of a text value |
| `XOR(`_x_`,` _y_`,` ... `,` _z_`)` | Boolean XOR of 1 or more arguments |
## Non-Formula Values
Values that are not formulas with recognized values (e.g. numbers, dollar amounts) will be interpreted and reformatted.
## Literal Text
To force a value to behave like text, prefix it with a `'`. E.g. `'0001` will be treated as regular text, not a number, and will not be reformatted. A text value beginning with an equal sign can be prevented from being interpreted as a formula in the same way. `'=A`. The leading apostrophe will be stripped when rendering the table cell. For a literal leading apostrophe, prefix with two apostrophes. `''Kay`
## Errors
If an expression cannot be evaluated, the cell will show an error symbol, such as `#REF`, `#SYNTAX`, or `#ERROR`. A more detailed message is in the `title` attribute and can be seen in a tooltip by mousing over it.
## Styling
The parser tries to be smart about differentiating operators from markdown syntax,
but if an operator character (such as `*`) is mistaken for formatting, escape
it with `\\*`.
A limited set of styling can be applied to formula results if it consists of
matching punctuation before and after. For example, `**=SUM(A:A)**` will
render a sum in bold. Up to three such formats can be combined, e.g.
`==~~__=SUM(A:A)__~~==`. Blank cells that are autofilled by a formula in the
column cannot currently be styled in this way.