Expr has two special values that are important in real scripts:
They are different and should be handled differently.
You will see `none()` when a value is missing. You will see `nan()` when a numeric result is invalid or unknown.
`none()` represents a missing value.
a = none(); a.is_none();
The final value is `true`.
Reading an unknown variable also returns `none()`.
missingValue;
The final value is `none()`.
This is useful because a script can detect missing values instead of always failing immediately.
`none()` behaves as false in conditions.
if(none()) { 'runs'; } else { 'does not run'; };
The final value is `'does not run'`.
You can test for `none()` explicitly:
value = none(); if(value.is_none()) { 'missing'; } else { 'available'; };
The final value is `'missing'`.
`none()` is not the same as `0`.
none() == 0; // false none() == none();
The second expression is true.
Do not use `none()` in numeric calculations.
5 + none(); // error
If a numeric value may be missing, check it before using it.
value = none(); if(value.is_none()) { result = 0; } else { result = value + 5; };
An `if` without an `else` produces `none()` when its condition is false.
value = if(false) { 10; }; value.is_none();
The final value is `true`.
This can be useful, but it can also cause errors if you use the result as a number.
result = 5 + if(false) { 10; };
This fails because the `if` produces `none()`.
Use an `else` branch when a value is required.
result = 5 + if(false) { 10; } else { 0; };
The final value of `result` is `5`.
Assigning `none()` explicitly clears or unsets the variable.
a = 10; a = none(); a;
The final value is `none()`.
There is one special assignment behavior with block-style control expressions.
If the right side is a block-style keyword expression that produces no value, assignment skips the update.
a = 10; a = if(false) { 20; }; a;
The final value is still `10`.
This protects existing values when an optional block produces no result.
Compound assignment does not use this skip behavior.
a = 10; a += if(false) { 20; };
This fails because compound assignment tries to calculate `10 + none()`.
`nan()` is a numeric value that means “not a valid number”.
value = nan(); value.is_nan();
The final value is `true`.
NaN can appear when a numeric operation or parsing step cannot produce a valid normal number.
value = nan() + 1; value.is_nan();
The final value is `true`.
NaN often propagates through numeric calculations.
`nan()` behaves as false in conditions.
if(nan()) { 'runs'; } else { 'does not run'; };
The final value is `'does not run'`.
Use `.is_nan()` when you specifically need to detect NaN.
value = nan(); if(value.is_nan()) { 'invalid number'; } else { 'valid number'; };
Use `.is_num_notnan()` when a value must be a valid finite number.
speed = 1200; if(speed.is_num_notnan() && speed >= 0) { 'valid speed'; } else { 'invalid speed'; };
This is useful before calculations that must not receive missing or invalid numeric values.
function SafeDivide(a, b) { if(!a.is_num_notnan() || !b.is_num_notnan()) { return none(); }; if(b == 0) { return none(); }; return a / b; } SafeDivide(10, 2);
The final value is `5`.
Some errors happen while a script is running.
Common runtime errors include:
Examples:
5 + none(); // invalid operand 10 / 0; // division by zero 1 << 64; // invalid shift count unknownFunc(); // undefined function
Parse errors happen before the script runs. They are syntax errors.
Common parse errors include:
Example:
a = 10 b = 20;
The first line is missing a semicolon.
Use `error(…)` when your script should stop with a clear message.
speed = -1; if(!speed.is_num_notnan() || speed < 0) { error('Invalid speed value'); };
This is useful in probing, ATC, dialogs, and machine workflow scripts where continuing with bad input would be unsafe or confusing.
Use specific error messages. They make debugging much easier.
Check assumptions before important operations.
function RequirePositiveNumber(value, name) { if(!value.is_num_notnan()) { error(name + ' must be a valid number'); }; if(value <= 0) { error(name + ' must be positive'); }; return value; } depth = RequirePositiveNumber(2.5, 'Depth');
Use this style for values that affect machine movement, probing decisions, tool changes, output control, or generated G-code.
Use `none()` when:
Use `nan()` when:
Use `error(…)` when:
Use an explicit fallback.
value = none(); if(value.is_none()) { value = 0; };
`is_num()` can include NaN. If you need a usable number, use `is_num_notnan()`.
value = nan(); value.is_num(); // true value.is_num_notnan(); // false
If an `if` expression must produce a number, include an `else` branch.
Read this script and predict the final value:
function ProbeStatus(errorValue) { if(errorValue.is_none()) { return 'missing'; }; if(!errorValue.is_num_notnan()) { return 'invalid'; }; if(errorValue <= 0.05) { return 'ok'; }; return 'too large'; } ProbeStatus(nan());
The final value is `'invalid'`.
Next: Complete examples