Operators
Precedence
Section titled “Precedence”Precedence decides how an expression groups when it mixes operators, from lowest to highest:
| Precedence | Operators | Description |
|---|---|---|
| 1 | |> | Pipeline |
| 2 | || | Logical or |
| 3 | && | Logical and |
| 4 | == != < > <= >= | Comparison |
| 5 | .. ..= | Range |
| 6 | + - | ^ | Add/subtract, bitwise or/xor |
| 7 | * / % << >> & &^ | Multiply/divide, shifts, bitwise and/and-not |
| 8 | as | Type conversion |
| 9 | - ! ^ & | Prefix (negation, not, bitwise not, reference) |
| 10 | . () [] ? .* | Postfix (access, call, index, propagate, deref) |
All binary operators are left-associative, so a repeated operator groups from the left.
a + b * cparses as a + (b * c)a && b || cparses as (a && b) || ca + b |> fparses as f(a + b)0..1 + 2parses as 0..(1 + 2)Value operators
Section titled “Value operators”Arithmetic
Section titled “Arithmetic”+, -, *, /, % require both operands to be the same numeric type. An untyped numeric literal adapts to the other operand, and unary - negates a number.
+ also concatenates strings:
let greeting = "hello" + ", " + "world"Comparison
Section titled “Comparison”== and != compare two values of the same comparable type. <, >, <=, >= compare numeric types and strings. All of them return bool.
let same = 2 == 2truelet ordered = "apple" < "banana"true, compared byte by byteLogical
Section titled “Logical”&& and || short-circuit: the right operand is not evaluated if the left determines the result. ! negates. All require bool operands.
if is_valid && count > 0 { process()}Bitwise
Section titled “Bitwise”&, |, ^, and &^ operate on integer values. Shifts (<<, >>) require an integer left operand and any integer right operand. The result has the left operand’s type.
let mask = 0b1111let value = 0b1010
let masked = value & masklet toggled = value ^ masklet shifted = value << 2let inverted = ^valueAccess operators
Section titled “Access operators”Indexed access
Section titled “Indexed access”Arrays and slices support integer indexing:
let nums = [10, 20, 30]let first = nums[0]10
let fixed: Array<int, 3> = [10, 20, 30]let second = fixed[1]20Maps support key indexing:
let mut ages = Map.new<string, int>()ages["Alice"] = 20let age = ages["Alice"]20Bracket access on an array or slice panics if the index is out of bounds. Bracket access on maps returns the zero value if the key is missing. If the map’s value type has no zero value (e.g. Ref<T>), bracket reads are rejected at compile time.
For access that cannot panic, use .get(), which returns an Option<T>.
Range indexing is available only on slices. To range-index an array, first copy its elements into a slice:
let tail = fixed.to_slice()[1..]| Syntax | Type | Description |
|---|---|---|
start..end | Range<T> | Exclusive upper bound |
start..=end | RangeInclusive<T> | Inclusive upper bound |
start.. | RangeFrom<T> | No upper bound |
..end | RangeTo<T> | Exclusive, no lower bound |
..=end | RangeToInclusive<T> | Inclusive, no lower bound |
The .. and ..= operators build these values, which drive a for loop or index a slice:
let slice = items[1..4]elements at indices 1, 2, 3Slice sub-slicing is safe by default. The resulting sub-slice has its capacity capped to its length, so append on a sub-slice always allocates a new backing array and never silently mutates the original.
Ref and deref
Section titled “Ref and deref”&expr points at a value instead of copying it, giving a Ref<T> that several places can hold at once. ref.* dereferences it, reading back the value it points at.
let x = 42let r = &xlet value = r.*42Expression operators
Section titled “Expression operators”Pipeline
Section titled “Pipeline”The pipeline operator |> passes the left side as the first argument to the function on the right.
x |> fequivalent to f(x)x |> f(y)equivalent to f(x, y)x |> f(y, z)equivalent to f(x, y, z)Chains read top to bottom:
let result = items |> filter(is_valid) |> map(transform) |> sum()equivalent to sum(map(filter(items, is_valid), transform))Lambdas are not allowed as pipeline targets.
Error propagation
Section titled “Error propagation”The ? operator propagates a failure.
Type conversion
Section titled “Type conversion”The as operator converts between numeric types.
Assignment operators
Section titled “Assignment operators”Simple assignment
Section titled “Simple assignment”= assigns to a mutable target.
let mut name = "Alice"name = "Bob"Compound assignment
Section titled “Compound assignment”+=, -=, *=, /=, %=, &=, |=, ^=, &^=, <<=, >>= combine an operation with an assignment.
let mut count = 0count += 1
let mut total = 10.0total *= 1.5