Dinamica EGO provides a family of five calculator functors that evaluate an algebraic or logical expression and return a result of a specific type. All five share the same underlying Image Expression Language, but they differ in what they output, how many expressions they accept, and which language features are available in each context.
| Functor | EGO Script Shorthand | Output Type | Evaluation context |
|---|---|---|---|
| Calculate Map | # | Raster map (continuous) | Once per cell across a spatial grid |
| Calculate Categorical Map | ## | Raster map (categorical) | Once per cell across a spatial grid |
| Calculate Value | $ | Single scalar value | Once, with no spatial or row context |
| Calculate Lookup Table Values | % | Lookup table (values computed) | Once per row of a base lookup table |
| Calculate Lookup Table Keys And Values | %% | Lookup table (keys and values computed) | Once per row — two separate expressions |
The shorthand symbols are also referred to as abbreviated syntax — both terms mean the same thing and are used interchangeably in this documentation and in the Dinamica EGO GUI options.
The expression language, including all arithmetic, logical, conditional, spatial, and stochastic operators, is described in full in The Expression Language section. Per-functor restrictions and the availability of each operator category are noted both in each functor's own section and in the relevant expression-language subsections. For a complete description of the EGO Script syntax used to call these functors — including the shorthand symbols, hook blocks, and conversion between forms — see Calculator functor shorthand in the EGO Script documentation.
Calculate Map computes a new continuous raster map cell by cell using an algebraic or logical expression. The expression is evaluated independently for every cell in the output map. The result is always computed as a real (floating-point) value and then converted to the output map's chosen cell type.
When an expression references more than one connected map, all of them are evaluated at the same current cell. The connected maps do not need matching extent, resolution, or pixel dimensions beforehand — Dinamica EGO reconciles this automatically at runtime through image virtualization — but they do need to share the same projection. See Co-located evaluation in section 4 for details.
| Name | Type | Required | Default | Description |
|---|---|---|---|---|
| Expression | Image Expression Type | Yes | — | The algebraic or logical formula used to compute each output cell. |
| Cell Type | Cell Type Type | No | Signed 32-bit Integer | Data type for each output cell (e.g., byte, int16, float32). |
| Null Value | Null Value Type | No | Based on Cell Type | Sentinel value representing “no data” in the output. |
| Result Is Sparse | Boolean Value Type | No | False | If True, only non-null cells are stored — saves memory but slows random access. |
| Result Format | Map Type | No | None | Optional reference map whose spatial format (extent, resolution, projection) is applied to the output. Category information in the reference map is ignored. |
| Name | Type | Description |
|---|---|---|
| Result | Map Type | The computed output map. |
All expression language features are available: image operators (iX, iX[line,col]), the line and column spatial keywords, lookup table operators (section 5), multi-column table operators (section 6), neighbourhood functions (nbMin, nbMax, nbAverage, etc. — section 7), neighbourhood indexing (nbMinRef, nbMaxRef — section 8), and the convolution operator (nbConvol — section 9).
Computes a new categorical raster map using an expression. Functionally identical to Calculate Map — the same inputs, parameters, and expression language apply — but the output is typed as a categorical map, which preserves category semantics for downstream functors that distinguish categorical maps from continuous maps (e.g., Calc Areas, For Each Category).
Use Calculate Categorical Map when the expression produces integer class codes rather than measured or continuous values. A common pattern is reclassifying a continuous map into discrete categories based on thresholds.
| Name | Type | Required | Default | Description |
|---|---|---|---|---|
| Expression | Image Expression Type | Yes | — | The formula used to compute each output cell's category code. |
| Cell Type | Cell Type Type | No | Signed 32-bit Integer | Data type for each output cell. |
| Null Value | Null Value Type | No | Based on Cell Type | Sentinel value representing “no data” in the output. |
| Result Is Sparse | Boolean Value Type | No | False | If True, only non-null cells are stored. |
| Result Format | Map Type | No | None | Optional reference map whose spatial format is applied to the output. |
| Name | Type | Description |
|---|---|---|
| Result | Categorical Map Type | The computed categorical output map. |
Identical to Calculate Map: all operators, spatial keywords, neighbourhood functions, indexing functions, and convolution are available.
Evaluates an expression once and returns a single scalar value. Because there is no current cell, row, or spatial grid, all image-based and neighbourhood operators are unavailable.
Calculate Value is used to compute a single parameter — such as a global threshold, a weighted sum of scalar inputs, or a value derived from a table — that can then be passed as input to other functors.
| Name | Type | Required | Default | Description |
|---|---|---|---|---|
| Expression | Image Expression Type | Yes | — | An expression that evaluates to a single numeric result. |
| Name | Type | Description |
|---|---|---|
| Result | Value Type | The computed scalar value. |
Available: all arithmetic and logical operators (sections 1 and 2), scalar value references (vX), and lookup table queries (tX[…]) in all single-key and multi-column forms (section 5, section 6).
Not available: image operators (iX, iX[line,col]), the line and column spatial keywords, neighbourhood functions, neighbourhood indexing functions, and the convolution operator. These all require a cell or row context that does not exist in Calculate Value.
Calculate Lookup Table Values evaluates an expression once per row of a base lookup table and writes the computed result as the value for that row in the output lookup table. The keys of the output table are inherited from the base table and are not recomputed.
When the base lookup table argument is .none, the row set is not a union of all connected tables. Instead it comes from a single connected lookup table: in the verbose form, this is the lookup table connected via the NumberTable port with the lowest index (e.g. t1 rather than t2); in the shorthand form, it is the first lookup table referenced by name in the expression.
| Name | Type | Required | Default | Description |
|---|---|---|---|---|
| Expression | Image Expression Type | Yes | — | Formula evaluated for each row. The result becomes the value for that row's key in the output table. |
| Key Column Name | String | Yes | — | Name of the key column in the output lookup table. |
| Value Column Name | String | Yes | — | Name of the value column in the output lookup table. |
| Base Lookup Table | Lookup Table Type | No | .none | A lookup table whose key set drives iteration. When .none, the lowest-indexed connected NumberTable (verbose form) or the first lookup table named in the expression (shorthand form) is used instead — not a union of all connected tables. |
| Name | Type | Description |
|---|---|---|
| Result | Lookup Table Type | A lookup table with keys from the base table and values computed by the expression. |
Within the expression, line refers to the key of the current row being iterated, not a spatial row index, and column refers to the value already associated with that key in the base lookup table — the row's own existing value, available without looking it up explicitly. This allows the expression to read the row's current value directly via column, and to look up related values from other connected tables using the current row's key: for example, t1[line] retrieves the value in table t1 whose key matches the row currently being computed.
Available: arithmetic and logical operators (sections 1 and 2), scalar references (vX), lookup table queries (tX[…]) in all single-key and multi-column forms (section 5, section 6), line (as the current row key), and column (as the current row's value in the base lookup table).
Not available: iX, iX[line,col], neighbourhood functions, neighbourhood indexing, and convolution. There is no spatial grid.
Calculate Lookup Table Keys And Values evaluates two separate expressions per row of a base lookup table — one for the key and one for the value — and writes both into the output lookup table. This allows complete transformation of a table's key-value structure, or construction of an entirely new lookup table row by row.
| Name | Type | Required | Default | Description |
|---|---|---|---|---|
| Key Column Expression | Image Expression Type | Yes | — | Formula evaluated for each row to produce the output key. |
| Value Column Expression | Image Expression Type | Yes | — | Formula evaluated for each row to produce the output value. |
| Key Column Name | String | Yes | — | Name of the key column in the output lookup table. |
| Value Column Name | String | Yes | — | Name of the value column in the output lookup table. |
| Base Lookup Table | Lookup Table Type | No | .none | A lookup table whose row set drives iteration. |
| Name | Type | Description |
|---|---|---|
| Result | Lookup Table Type | A lookup table with both keys and values computed by the respective expressions. |
Same as Calculate Lookup Table Values: line represents the key of the current row in the base table, and column represents the value already associated with that key; vX and tX[…] are available (sections 5 and 6); spatial and image operators are not. Both the key expression and the value expression share the same set of connected operands.
All data referenced in any expression must be connected to the functor's ports before writing the expression. This is done through hook functors — Number Map, Number Table, and Number Value — which bind a connected data source to a numbered identifier used inside the expression. The same port types apply across all five functors:
Tip: Give every connected functor a descriptive alias. The expression editor lists all available identifiers with their aliases at the top, making complex models much easier to read and maintain. The alias is also what generates the functor's variable name, and that variable name is exactly what the shorthand notation references: a map aliasedregions, for example, is bound to the variableregionsand is then referenced in a shorthand expression as#regions, a table or lookup table as%regions, and a value as$regions. See Calculator functor shorthand for details on the shorthand notation.
Note: Map hook connections (NumberMap/iX) are only meaningful in Calculate Map and Calculate Categorical Map. In Calculate Value, Calculate Lookup Table Values, and Calculate Lookup Table Keys And Values there is no cell context, andiXreferences cannot be used in the expression.
The expression is written in Dinamica EGO's Image Expression Language — a concise algebra where every term operates on the current evaluation unit (a cell, a table row, or nothing, depending on the functor). The language has eight categories of operators and functions described below.
Unless a restriction is noted, every operator is available in all five calculator functors.
| Symbol | Refers to | Available in |
|---|---|---|
iX | Value of map X at the current cell | Calculate Map, Calculate Categorical Map only |
tX | Connected table or lookup table X (used with a bracket operator) | All five functors |
vX | Connected scalar value X | All five functors |
line | Spatial row index of the current cell, starting at 1 (map calculators) or key of the current row (table calculators) | All except Calculate Value |
column | Spatial column index of the current cell, starting at 1 (map calculators) or value associated with the current row's key (table calculators) | All except Calculate Value |
X ranges from 1 to 100. In logical expressions, zero is false and any non-zero value is true.
The table below lists all infix and prefix operators in descending precedence order (highest precedence = evaluated first). All operators are available in all five calculator functors.
| Precedence | Operator | Syntax | Description | Example |
|---|---|---|---|---|
| 1 | Conditional | if EXPR then EXPR else EXPR | Evaluates to the second expression if the condition is true, otherwise the third. Can be nested. | if i1 > 0 then i1 else 0 |
| 2 | Boolean Or | EXPR or EXPR / EXPR || EXPR | True if either argument is true. Short-circuit evaluated — the right side is skipped if the left is already true. | isNull(i1) || i1 > 100 |
| 2 | Boolean And | EXPR and EXPR / EXPR && EXPR | True only if both arguments are true. Short-circuit evaluated — the right side is skipped if the left is already false. | not isNull(i1) and i1 > 0 |
| 3 | Equal | EXPR = EXPR / EXPR == EXPR | True if both sides are equal. | i1 == 2 |
| 3 | Not Equal | EXPR != EXPR / EXPR /= EXPR / EXPR <> EXPR | True if both sides differ. | i1 != 0 |
| 4 | Greater Than | EXPR > EXPR | i1 > i2 |
|
| 4 | Greater Than Or Equal | EXPR >= EXPR | i1 >= v1 |
|
| 4 | Less Than | EXPR < EXPR | i1 < 100 |
|
| 4 | Less Than Or Equal | EXPR ⇐ EXPR | i1 ⇐ i2 |
|
| 5 | Add | EXPR + EXPR | i1 + i2 |
|
| 5 | Subtract | EXPR - EXPR | i1 - i2 |
|
| 6 | Multiply | EXPR * EXPR | i1 * 2.5 |
|
| 6 | Divide | EXPR / EXPR | i1 / i2 |
|
| 6 | Modulo | EXPR % EXPR | Remainder after integer division | i1 % 100 |
| 7 | Power | EXPR ^ EXPR | Exponentiation | i1 ^ 3 |
| 8 | Catch Error (?) | EXPR ? EXPR | If the left expression produces an algebraic error (division by zero, key not found, etc.), return the right expression instead. | (i1 / i2) ? (i1 - i2) |
| 9 | Boolean Not | not EXPR / ! EXPR | Inverts a boolean value. | not isNull(i1) |
| 9 | Negate | -EXPR | Arithmetic negation. | -ceil(i1 + i2) |
Note on null and equality: Writingi1 == nulldoes not test for null — because null participates in no arithmetic comparison, it always produces null itself, poisoning the expression. Always useisNull(i1)instead. See the Null Value Handling section for full details.
All mathematical functions are available in all five calculator functors.
| Function | Syntax | Description | Example | |
|---|---|---|---|---|
| Square Root | sqrt(EXPR) | sqrt(i1 / i4) | ||
| Sin | sin(EXPR) | Sine; input in radians | sin(i1 / i4) | |
| Cos | cos(EXPR) | Cosine; input in radians | cos(i1 + i2) | |
| Tan | tan(EXPR) | Tangent; input in radians | tan(i1 * i5 + 6) | |
| Acos | acos(EXPR) | Arccosine; output in radians | acos(i1 + i2) | |
| Asin | asin(EXPR) | Arcsine; output in radians | asin(i1 + i2) | |
| Atan | atan(EXPR) | Arctangent; output in radians | atan(i1 + i2) | |
| Exp | exp(EXPR) | Natural exponential (e | x) | exp(i1 + i2) |
| Natural Logarithm | ln(EXPR) | log base e | ln(i1 / i4) | |
| Log base 10 | log(EXPR) | log(i1 / i4) | ||
| Absolute Value | abs(EXPR) | abs(i1 + i2) | ||
| Ceiling | ceil(EXPR) | Smallest integer >= value | ceil(i1 + i2) | |
| Floor | floor(EXPR) | Largest integer ⇐ value | floor(i1 + i2) | |
| Round | round(EXPR) | Round to nearest integer | round(i1 / i4) | |
| Maximum | max(EXPR, EXPR) | Greater of two values | max(i1, i2) | |
| Minimum | min(EXPR, EXPR) | Lesser of two values | min(i1, i4) | |
| Signal | signal(EXPR) | Returns +1 if positive, -1 if negative, 0 if zero | signal(i1 - 4) | |
| Pi | pi | The constant pi (3.14159265358979323846) | i1 * pi / 180 |
| Function | Syntax | Description | Example |
|---|---|---|---|
| Clamp | clamp(EXPR, EXPR_MIN, EXPR_MAX) | Constrains a value to [min, max]. Equivalent to: if EXPR < MIN then MIN else if EXPR > MAX then MAX else EXPR | clamp(v1, 1, 12) |
| ClampMod | clampMod(EXPR, EXPR_MIN, EXPR_MAX) | Like clamp, but wraps around using modulo when the value is outside the range. Useful for cyclic quantities such as years or angles. Approximately: (EXPR - MIN) % (MAX - MIN + 1) + MIN | clampMod(v1, 2010, 2054) |
These functions generate a new random sample for each evaluation unit each time the expression is evaluated. In Calculate Map and Calculate Categorical Map, this means one sample per cell, making them suitable for spatially stochastic models. In Calculate Lookup Table Values and Calculate Lookup Table Keys And Values, one sample is drawn per table row. In Calculate Value, a single sample is drawn for the whole expression.
| Function | Syntax | Description | Example |
|---|---|---|---|
| Uniform (0-1) | rand | Generates a random value uniformly in [0, 1). Used as a keyword, not a function call. | if rand > 0.5 then 1 else i2 |
| Uniform (bounded) | rUniform(EXPR_MIN, EXPR_MAX) | Generates a random value uniformly between the given bounds. | if rUniform(12, 15) > 14 then 1 else i2 |
| Normal | rNormal(EXPR_MEAN, EXPR_STDDEV) | Generates a random value from a Normal (Gaussian) distribution with the given mean and standard deviation. | if rNormal(10, 2) > 9 then 1 else i2 |
| Poisson | rPoisson(EXPR_LAMBDA) | Generates a random integer from a Poisson distribution with the given lambda. | if rPoisson(100) > 95 then 1 else i2 |
| Function | Syntax | Description | Example |
|---|---|---|---|
| Literal value | 2, -3.5e-2, etc. | Any numeric literal, including scientific notation. | 2 + i1 / -3.5e-2 |
| Abort | abort | Immediately halts model execution. Useful as a guard inside a conditional to catch unexpected states. | if i1 > 0 then i1 * i2 + 4 else abort |
Available in all five calculator functors.
| Operator | Syntax | Description | Example |
|---|---|---|---|
| Get Variable Value | vX | Returns the scalar (constant) value connected to port X. | v1 + t1[v2 + 4] |
Availability: Calculate Map and Calculate Categorical Map only. These operators require a cell context that does not exist in Calculate Value, Calculate Lookup Table Values, or Calculate Lookup Table Keys And Values.
Exception:lineandcolumnare also available in the two lookup table calculators, where they take on row-oriented meanings instead of spatial ones:lineis the key of the current row, andcolumnis the value associated with that key in the base lookup table being iterated.
| Operator | Syntax | Description | Example |
|---|---|---|---|
| Get Image Value | iX | Returns the value of image X at the current cell. | i2 |
| Get Image Value At Location | iX[LINE_EXPR, COL_EXPR] | Returns the value of image X at the specified (line, column) coordinate. If the target cell is null, returns 0 (not null). | i1[line - 1, column - 2] |
| Get Image Null Value | null | Returns the null sentinel value for the current output image, making the current cell null. Using null in arithmetic always poisons the result. | if i1 > 2 then i1 else null |
| Get Image Null Value (specific) | null(iX) | Returns the null sentinel value defined for image X specifically. | if null(i2) > 2 then 1 else null |
| Is Null | isNull(EXPR) | Returns 1 if the expression result is null, 0 otherwise. The correct way to test for null. | if not isNull(i1) then i1 else i2 |
| Get Line Number | line | In map calculators: returns the row index of the current cell, counting from 1. In lookup table calculators: returns the key of the current row. | line + 1 |
| Get Column Number | column | In map calculators: returns the column index of the current cell being processed, counting from 1. In lookup table calculators: returns the value associated with the key of the current row in the base lookup table. | if column / 2 > 50 then 1 else null |
Co-located evaluation. When an expression references more than one map (i1,i2, …), the current cell is shared: everyiXis evaluated at the samelineandcolumnfor each step of the calculation, soi1andi2always refer to the same spatial location, not just “image 1” and “image 2” in some generic sense. The connected maps do not need to have matching extent, resolution, or pixel dimensions beforehand — Dinamica EGO reconciles this automatically through image virtualization: each input map is transparently wrapped in a virtual version sharing a common extent and the highest resolution among the inputs, so that “the current cell” lines up to the same point on the ground across all of them. The one requirement that virtualization does not relax is projection — all maps given to the calculator at the same time must share the same projection.iX[LINE_EXPR, COL_EXPR]breaks the shared-cell default, letting an expression sample a given image at an explicit coordinate instead of the current cell.
lineandcolumnin map calculators are invaluable for creating geometric masks, distance ramps, or for passing precise coordinates intoiX[LINE, COL]lookups. Both are 1-indexed — the top-left cell of the map is atline = 1, column = 1, not 0. In Calculate Lookup Table Values and Calculate Lookup Table Keys And Values, both keywords serve a different, row-oriented role:lineis the key of the current table row, andcolumnis the value already associated with that key in the base lookup table — socolumnlets the expression read the row's existing value without a separate table lookup, whilet1[line](or%someTable[line]in shorthand) reads the corresponding value from any other connected table.
These operators query a Lookup Table (tX) — a single-key table — and return the associated value. The key lookup rule is controlled by a prefix operator inside the brackets. Available in all five calculator functors.
General syntax: tX[RULE EXPR]
IftXis bound to a multi-column Table (not a Lookup Table), an error is reported. See section 6 for multi-column tables.
| Operator | Syntax | Description | Example |
|---|---|---|---|
| Exact match | tX[EXPR] | Returns the value whose key equals the expression. Returns null if not found. | t2[i1 + 2] |
| Equal lower bound | tX[⇐ EXPR] | Returns the value for the greatest key ⇐ EXPR. | t2[⇐ 14] |
| Strict lower bound | tX[< EXPR] | Returns the value for the greatest key < EXPR. | t2[< i1 + 2] |
| Equal upper bound | tX[>= EXPR] | Returns the value for the smallest key >= EXPR. | t2[>= i1 + i3] |
| Strict upper bound | tX[> EXPR] | Returns the value for the smallest key > EXPR. | t2[> i7] |
| Closest key | tX[>< EXPR] | Returns the value for the key nearest to EXPR (ties go to the lower key). | t2[>< 3 + i7] |
| Linear interpolation | tX[/ EXPR] | Returns a linearly interpolated value between the two surrounding keys. | t2[/ i2] |
| Key existence test | tX[? EXPR] / tX[=? EXPR] / tX[==? EXPR] | Returns 1 if EXPR matches a key in the table, 0 otherwise. Does not retrieve a value. | t2[? i2] |
| Named attribute | tX[“NAME”] | Returns the value bound to a predefined attribute name (e.g. “cellArea”). Only valid for tables produced by Extract Map Attributes or Extract Lookup Table Attributes. | t2[“cellArea”] |
The bound operators (⇐, <, >=, >, ><, /) are especially useful for range-based reclassification and interpolation, where your table defines breakpoints rather than exact class codes.
These operators query a regular Table (tX) — one with multiple key columns and one or more data columns — using a set of keys simultaneously. Available in all five calculator functors.
General syntax: tX[ [KEY1, KEY2, …] ] or tX[ [KEY1, KEY2, …] [COL] ]
IftXis bound to a Lookup Table (single-key), an error is reported.
| Operator | Syntax | Description | Example |
|---|---|---|---|
| Default column | tX[ [EXPR, EXPR, …] ] | Returns the value in the first data column matching the given set of keys. | t2[ [i1 + 2, i2/2, t1[v2]] ] |
| Named column | tX[ [EXPR, EXPR, …] [“COL_NAME”] ] | Returns the value in the named data column matching the given set of keys. | t2[ [i1 + 2, i2/2, t1[v2]] [“Area_In_Hectares”] ] |
| Indexed column | tX[ [EXPR, EXPR, …] [EXPR] ] | Returns the value in the column indexed by the second expression matching the given set of keys. | t2[ [i1 + 2, i2/2, t1[v2]] [v1+2] ] |
These operators allow joining spatial data to rich tabular datasets at the cell level — for example, retrieving a transition probability from a multi-dimensional probability table keyed by land-use class and elevation zone.
Availability: Calculate Map and Calculate Categorical Map only. A spatial grid is required.
Neighborhood operators aggregate values from a rectangular window centred on the current cell.
Full syntax: nbN(IMAGE, h, w, y, x)
Short syntax (window centred on current cell): nbN(IMAGE, h, w)
| Parameter | Meaning |
|---|---|
N | Operator name (see table below) |
IMAGE | An image identifier (iX) |
h | Number of window rows |
w | Number of window columns |
y | Row coordinate to anchor the window centre (optional) |
x | Column coordinate to anchor the window centre (optional) |
The window centre defaults to the current cell when y and x are omitted. For even-sized windows, the centre is displaced toward the top-left corner. Null cells within the window are excluded from all calculations.
| Operator | Syntax | Description | Example | |
|---|---|---|---|---|
| Minimum | nbMin(…) | Minimum value among non-null cells in the window | nbMin(i4, 2, 3, line-1, column) | |
| Maximum | nbMax(…) | Maximum value among non-null cells in the window | nbMax(i1, 4, 4) - 1 | |
| Sum | nbSum(…) | Sum of non-null cells in the window | nbSum(i3, 5, 5) + 7 | |
| Product | nbProd(…) | Product of all non-null cells in the window | if not isNull(i1) then nbProd(i1, 2, 2, 0, column) else 0 | |
| Count | nbCount(…) | Number of non-null cells in the window | nbCount(i2, 3, 3) + nbCount(i1, 3, 3, line, column+3) | |
| Average | nbAverage(…) | Arithmetic mean of non-null cells in the window | round(nbAverage(i1, 7, 7)) | |
| Median | nbMedian(…) | Median of non-null cells. For an even count, the greater of the two central values is returned. | nbMedian(i1, 5, 5) | |
| Mode | nbMode(…) | Most frequent value among non-null cells. Returns null if no mode exists; returns the lesser value if multiple modes tie. | nbMode(i1, 5, 5) | |
| Variance | nbVar(…) | Population variance of non-null cells: sum of (xi - mean) | 2 / n | nbVar(i4, 7, 7) / 25 |
| Standard Deviation | nbStdDev(…) | Population standard deviation of non-null cells: sqrt of variance | nbStdDev(i2, 3, 3, line+1, column) |
Availability: Calculate Map and Calculate Categorical Map only.
These operators compute a neighbourhood statistic and then use the result as an index to retrieve a value from either a lookup table or a second image.
Full syntax:
nbN(IMAGE, h, w, TABLE, y, x)
nbN(IMAGE, h, w, IMAGE2, y, x)
Short syntax (window centred on current cell):
nbN(IMAGE, h, w, TABLE)
nbN(IMAGE, h, w, IMAGE2)
When a TABLE is provided: the statistic is used as a key to query the lookup table.
When an IMAGE2 is provided: the statistic is used as a pixel coordinate to sample IMAGE2.
| Operator | Syntax | Description | Example |
|---|---|---|---|
| MinRef | nbMinRef(…) | Finds the minimum in the window, then uses it as an index. | nbMinRef(i4, 2, 3, t1, line, column) |
| MaxRef | nbMaxRef(…) | Finds the maximum in the window, then uses it as an index. | nbMaxRef(i4, 2, 3, i1, line, column) |
Availability: Calculate Map and Calculate Categorical Map only.
nbConvol applies a kernel-weighted convolution to an image — for spatial filtering such as Gaussian blur or edge detection.
Syntax: nbConvol(IMAGE, TABLE, h, w) / nbConvol(IMAGE, TABLE, h, w, y, x)
| Parameter | Meaning |
|---|---|
IMAGE | The image to convolve (iX) |
TABLE | A Table whose entries are the kernel coefficients, indexed 1 to h*w, mapped left-to-right, top-to-bottom |
h | Number of kernel rows |
w | Number of kernel columns |
y, x | Anchor position (optional; defaults to window centre) |
Kernel index mapping for a 3×3 kernel (h=3, w=3):
| Table key | Window position |
|---|---|
| 1 | top-left |
| 2 | top-centre |
| 3 | top-right |
| 4 | mid-left |
| 5 | centre |
| 6 | mid-right |
| 7 | bottom-left |
| 8 | bottom-centre |
| 9 | bottom-right |
Example: Apply a Gaussian-blur kernel stored in t1 over a 3×3 window on i1:
nbConvol(i1, t1, 3, 3)
A null value in any operand poisons the entire expression: the result becomes null regardless of what the rest of the expression does. This is not a special case — it is the default behaviour for every operator and every operand type, across all five calculator functors.
| Expression | Null behaviour |
|---|---|
i1 / 0 | Always null (division by zero on a map cell) |
v1 / 0 | Always null — division by zero is null regardless of operand type |
t1[v1] | Null if the key v1 is not found in lookup table t1 |
i1 + t1[line] / v1 ^ 3 | Null if the map cell i1, the table lookup t1[line], or the value v1 is null |
if isNull(t1[v1]) then 1 else 2 | Never null — isNull itself always resolves to 0 or 1 |
if isNull(v1) then i2 else t1[line] | May be null, depending on i2 or the table lookup t1[line] |
(100 / v2) ? 0 | Never null — div-by-zero on a value falls back to 0 |
(t1[v1]) ? i1 | If the key v1 is not found in t1, falls back to i1; may still be null if i1 is null |
The poison spreads through the entire chain: if i1 is null, then i1 + 5 is null, (i1 + 5) * v1 is null, and so on. There is no way to “un-null” a result once a null has entered the calculation — except by explicitly testing for it first.
In a realistic expression, null can enter from several independent sources simultaneously. This expression computes a weighted transition probability from two input maps and a per-class calibration table:
(i1 * t1[i3] + i2 * (1 - t1[i3])) / v1
Here i1 is a distance map, i2 a slope map, i3 a land-use class map, t1 a calibration table keyed by class code, and v1 a normalisation scalar. The result is null if any of the following is true at the current cell: i1, i2, or i3 is null; the class code in i3 is not a key in t1; or v1 is zero. A single missing class in the calibration table silently nulls every cell of that class, which may be difficult to diagnose. The defensive form makes each failure mode explicit:
if isNull(i1) or isNull(i2) or isNull(i3) then null else (i1 * (t1[i3] ? 0) + i2 * (1 - (t1[i3] ? 0))) / v1
The ? operator provides a fallback of 0 for any missing table key, so cells whose class is absent from the calibration table are treated as having zero weight rather than propagating null.
Two safe patterns for handling nulls — applicable to map cells, table lookups, and scalar values alike:
isNull(EXPR) — test for null and branch:if isNull(t1[v1]) then 0 else t1[v1]
EXPR ? FALLBACK — catch any algebraic error and substitute a fallback:(v1 / v2) ? 0
Note:isNull()is immune to the poisoning rule — it always returns 0 or 1, never null, even when its argument is null. It is the only reliable way to branch on null.
If the computed real value exceeds the range of the chosen Cell Type, that cell is also written as null rather than wrapping or clipping. This range check applies to the map calculators only, since the other calculator functors do not write to a typed cell grid.
Availability: Calculate Map and Calculate Categorical Map only. The two exceptions below involveiXreferences and neighbourhood functions, which do not exist in the other three calculator functors.
iX[LINE_EXPR, COL_EXPR] — accessing a map at a specific coordinate returns 0, not null, when the target cell is null. This is the one case where a null input does not poison the output. It can be a source of subtle bugs: an expression that tests i1[line-1, column] > 0 will silently treat a null neighbour as zero rather than null. A table or lookup-table key lookup (tX[EXPR]) that finds no matching key still returns null as normal — this exception applies only to map coordinate lookups.nbN(iX, h, w) — operators such as nbSum, nbAverage, nbMax, and so on aggregate over a window of cells and exclude null cells from the calculation. If i1 is null at the current cell, the neighbourhood function simply ignores it and aggregates the remaining non-null cells in the window.
When writing expressions inside a .ego script file (see EGO Script Language), the expression must be enclosed in square brackets [ ]. Below are examples of each functor in both shorthand and verbose form.
A note on operand naming. Throughout the expression-language tables above, operands are written generically asiX,tX, andvX— the numbered form, used when a port is connected via an explicit hook functor (NumberMap,NumberTable, orNumberValue) in the verbose form below. EGO Script's shorthand form instead refers to operands by name — the variable already bound elsewhere in the script — prefixed with a sigil that marks its type:#for a map,%for a table or lookup table,$for a value. Soi1in a verbose expression corresponds to#someMapVariablein the shorthand version of the same expression,t1corresponds to%someTableVariable, andv1corresponds to$someValueVariable. The two forms are interchangeable but cannot be mixed within a single expression. See Calculator functor shorthand in the EGO Script documentation for a full description of both forms.
// Shorthand — normalise a map to the [0, 1] range
result := # [ (#inputMap - $minVal) / ($maxVal - $minVal) ] .float32 .default .no .none;
// Verbose equivalent
result := CalculateMap {
expression = [ (i1 - v1) / (v2 - v1) ],
cellType = .float32,
nullValue = .default,
resultIsSparse = .no,
resultFormat = .none
} {{
// i1
NumberMap inputMap 1;
// v1
NumberValue minVal 1;
// v2
NumberValue maxVal 2;
}};
// Shorthand — reclassify a continuous map into three categories
landUse := ## [
if #elevationMap < $lowThreshold then 1
else if #elevationMap < $highThreshold then 2
else 3
] .int8 .default .no .none;
// Verbose equivalent
landUse := CalculateCategoricalMap {
expression = [
if i1 < v1 then 1
else if i1 < v2 then 2
else 3
],
cellType = .int8,
nullValue = .default,
resultIsSparse = .no,
resultFormat = .none
} {{
// i1
NumberMap elevationMap 1;
// v1
NumberValue lowThreshold 1;
// v2
NumberValue highThreshold 2;
}};
// Shorthand — compute a weighted combination of two scalar inputs
blendedRate := $ [ $weight * $rateA + (1 - $weight) * $rateB ];
// Verbose equivalent
blendedRate := CalculateValue {
expression = [ v1 * v2 + (1 - v1) * v3 ]
} {{
// v1
NumberValue weight 1;
// v2
NumberValue rateA 2;
// v3
NumberValue rateB 3;
}};
// Shorthand — look up a scalar threshold from a calibration table
threshold := $ [ %calibrationTable[$targetClass] ];
// Verbose equivalent
threshold := CalculateValue {
expression = [ t1[v1] ]
} {{
// t1
NumberTable calibrationTable 1;
// v1
NumberValue targetClass 1;
}};
// Shorthand — mark each row in a lookup table where value meets a threshold
hilltops := % [
if %saddleHeights[line] >= $minimumHeight and %saddleAngles[line] >= $minimumSlopeAngle then 1 else null
] "Top_Id" "Is_Hilltop" .none;
// Verbose equivalent
hilltops := CalculateLookupTableValues [
if t1[line] >= v1 and t2[line] >= v2 then 1 else null
] "Top_Id" "Is_Hilltop" .none {{
// t1
NumberTable saddleHeights 1;
// t2
NumberTable saddleAngles 2;
// v1
NumberValue minimumHeight 1;
// v2
NumberValue minimumSlopeAngle 2;
}};
// Shorthand — transform values using a calibration lookup table, iterating base table keys
dominantTops := % [
if %dominanceLookup[line] = line then 1 else null
] "Top_Id" "Is_Dominant" dominanceLookup;
// Shorthand — extract two columns from a multi-column table into a new lookup table
nearestDistances := %% {
keyColumnExpression = [ %nearestPoints[[line]["Point_Id"]] ],
valueColumnExpression = [ %nearestPoints[[line]["Nearest_Distance"]] ],
keyColumnName = "Point_Id",
valueColumnName = "Nearest_Distance",
baseLookupTable = pointKeys
};
// Verbose equivalent
nearestDistances := CalculateLookupTableKeysAndValues [
t1[[line]["Point_Id"]]
] [
t1[[line]["Nearest_Distance"]]
] "Point_Id" "Nearest_Distance" pointKeys {{
// t1
NumberTable nearestPoints 1;
}};
(i1 - v1) / (v2 - v1)
i1 = input map; v1 = global minimum, v2 = global maximum.
i1 * v1 + i2 * (1 - v1)
i1, i2 = the two maps to blend; v1 = blending weight.
sin(i1 * pi / 180)
i1 = map of values in degrees.
clamp(i1 * v1 + i2 * v2, 0, 1)
i1, i2 = input maps; v1, v2 = their respective blending weights.
if isNull(i1) then nbAverage(i1, 3, 3) else i1
i1 = input map.
nbMax(i1, 5, 5) - nbMin(i1, 5, 5)
i1 = input map.
i1 + rNormal(0, v1)
i1 = input map; adds Gaussian noise with zero mean and standard deviation v1 to every cell.
line / v1
Produces a north-to-south gradient scaled by scalar v1.
i2[round(i1), column]
For each cell, samples i2 at the row given by image i1, same column.
(i1 / i2) ? (i1 - i2)
i1 = numerator map, i2 = denominator map. If i2 is zero at a cell, falls back to i1 - i2 instead of producing null.
if i1 == 2 then 1 else 0
i1 = input categorical map.
if i1 == 1 then 10 else if i1 == 2 then 20 else if i1 == 3 then 35 else null
i1 = input categorical map.
t1[<= i1]
i1 = continuous input map; t1 = breakpoint lookup table mapping value thresholds to category codes. Assigns each cell the category value from t1 whose key is the greatest key ⇐ the cell value — implementing interval-based reclassification without if/else chains.
if i1 > v1 and i2 < v2 then 1 else if i1 > v1 then 2 else 3
i1 = slope map, i2 = distance map; v1, v2 = threshold scalars.
if %regionCounts[?#regions] then 1 else null
Assigns category 1 to every cell whose region identifier (map regions) appears as a key in lookup table regionCounts, null otherwise. Written in shorthand: the map is referenced as #regions and the lookup table as %regionCounts.
v1 * v2 + (1 - v1) * v3
v1 = weight, v2, v3 = the two values to blend.
t1[v1]
t1 = calibration lookup table, v1 = the key to look up.
v1 + 1
When v1 holds the previous iteration's counter value, this computes the next step.
(v1 - v2) / (v3 - v2)
Normalises v1 to the range defined by v2 (minimum) and v3 (maximum).
if t1[line] >= v1 and t2[line] >= v2 then 1 else null
t1, t2 = operand lookup tables; v1, v2 = threshold values. Iterates over all row keys; t1[line] and t2[line] retrieve the corresponding values from each table.
t1[line] * v1
Scales every value in table t1 by a constant v1, producing a new lookup table with the same keys.
if t1[line] = line then 1 else null
Returns 1 for rows where the value stored under that key equals the key itself.
t1[<= line]
For each key, looks up the value from t1 whose key is the greatest key ⇐ the current row key — interpolating class membership from a breakpoint table.
// Key expression t1[[line]["Point_Id"]] // Value expression t1[[line]["Nearest_Distance"]]
For each row in the base lookup table, the key is drawn from the “Point_Id” column of t1 and the value from “Nearest_Distance”.
// Key expression line * 10 // Value expression t1[line] / v1
t1 = base lookup table being iterated; v1 = scaling divisor. Multiplies each key by 10 and divides the corresponding value by v1.
t1[ [i1, i2] ["TransitionProb"] ]
i1, i2 = map layers providing the composite key values; t1 = multi-key probability table. Looks up a transition probability using two map values as composite keys. Available in Calculate Map and Calculate Categorical Map; the same syntax works in the table calculators by substituting line or vX for iX.
The steps differ by group of calculator functors. Each group is described separately below.
.none, in which case the row set instead comes from a single connected table — the lowest-indexed NumberTable in verbose form, or the first lookup table referenced by name in the expression in shorthand form.line for the current row's key and column for the current row's existing value where needed.line and column are context-dependent. In Calculate Map and Calculate Categorical Map, line is the spatial row index and column is the spatial column index of the current pixel, both starting at 1. In Calculate Lookup Table Values and Calculate Lookup Table Keys And Values, both are still available but take on row-oriented meanings: line is the key of the current table row, and column is the value already associated with that key in the base lookup table. A different table's value for that same key can be retrieved with %someTable[line]. See section 4 for full details.nbN operators (section 7) skip null cells in their window; only non-null cells contribute to the statistic.iX[LINE, COL] returns 0, not null, for out-of-bounds or null cells. This is the one exception to the general null-propagation rule. See section 4 and Null Value Handling.| Functor | Internal name |
|---|---|
| Calculate Map | CalculateMap |
| Calculate Categorical Map | CalculateCategoricalMap |
| Calculate Value | CalculateValue |
| Calculate Lookup Table Values | CalculateLookupTableValues |
| Calculate Lookup Table Keys and Values | CalculateLookupTableKeysAndValues |