Argentum blocks can be marked with '=name
' labels that are visible from inner sub-statements. They are used in ^leave
statements.
{=label
i < 0 ? ^label;
log("positive"); // this line won't be executed if `i` < 0
}
Leave-statement can have a parameter - expression that produces result
echo({=sign
i < 0 ? ^sign="negative";
i > 0 ? ^sign="positive";
"zero"
})
It reads as "here's a block "sign". If 'i<0' terminate block 'sign' with value "negative". If 'i>0', terminate it with value "positive". Otherwise end this block naturally with result "zero".
There are also implicit labels:
- Function/method name plays the role of function body label.
- Variable initializer can "leave" using variable name as a label:
Example:
sign = {
i<0 ? ^sign = -1;
i>0 ? ^sign = 1;
0
};
fn myFunction() {
loop {
otherFn() ? ^myFunction // if (otherFn()) return;
}
}
The "leave expression" has a special uninhabited "no_return" type that is compatible to all types because it will never be converted to these types. You can declare return types of callables as "no_return" too.
Additionally this operator supports stack unwinding and allows to pass control between functions, effectively acting as exception handling mechanism.