mshell provides control flow constructs for conditional execution and looping.
The if block is the primary conditional construct.
The condition is evaluated before if and popped from the stack.
true if
"condition was true" wl
end
Add an else branch for when the condition is false:
false if
"true branch" wl
else
"false branch" wl
end
Use else* and *if for else-if chains:
2 n!
@n 1 = if
"one" wl
else* @n 2 = *if
"two" wl
else* @n 3 = *if
"three" wl
else
"other" wl
end
Conditions can be booleans or integers. For integers, 0 is true (like Unix exit codes), non-zero is false.
0 if "zero is true" wl end
1 if "not printed" wl end
iff is a postfix conditional that executes quotations based on a condition.
It has two forms: with and without a false branch.
# Two-argument form: condition (true-quote) iff
true ("was true" wl) iff
# Three-argument form: condition (true-quote) (false-quote) iff
false ("true" wl) ("false" wl) iff
iff is useful for inline conditionals:
@count 0 > (@items process) iff
loop repeatedly executes a quotation until break is called.
0 i!
(
@i 5 >= if break end
@i wl
@i 1 + i!
) loop
Output:
0
1
2
3
4
break exits the innermost loop.
0 i!
(
@i 1 + i!
@i 3 = if
"breaking" wl
break
end
@i wl
) loop
"done" wl
Output:
1
2
breaking
done
continue skips the rest of the current iteration and starts the next one.
0 i!
(
@i 5 >= if break end
@i 1 + i!
@i 3 = if continue end
@i wl
) loop
Output (3 is skipped):
1
2
4
5
Prefix quotes provide an alternative syntax for applying functions to quotations.
The syntax is functionName. ... end, which is equivalent to (...) functionName.
# Traditional postfix syntax
[1 2 3 4 5] (3 >) filter
# Prefix quote syntax
[1 2 3 4 5] filter. 3 > end
Prefix quotes work with any function that expects a quotation, including map, filter, each, and user-defined functions:
# Double each element
[1 2 3] map. 2 * end # Result: [2 4 6]
# Print each item
["a" "b" "c"] each. wl end
Prefix quotes can be chained:
# Filter positives, then double them
[-1 2 -3 4] filter. 0 > end map. 2 * end # Result: [4 8]
Prefix quotes can also be nested (one inside another):
# For each sublist, filter elements > 5
[[1 2 3] [4 5 6] [7 8 9]] map. filter. 5 > end end # Result: [[] [6] [7 8 9]]
This is also useful to turn boolean operators and and or into
a more traditional lookup infix format:
true or. false end and. true end # Like (true | false) & true = true