Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Choosing numeric types in expressions

Type arguments go before the call: range[u8](8). A collection annotation or function return type can also guide a directly written range comprehension.

def squares() -> Result[list[u8], AllocError | OverflowError[u8] | ZeroDivisionError]:
    [n * n for n in range(8) if n % 2 == 0]

def main() -> Result[(), AllocError | IoError | OverflowError[u8] | OverflowError[u16] | ZeroDivisionError]:
    print(squares()?)?
    print([n * n for n in range[u8](8) if n % 2 == 0]?)?
    small: list[u16] = [n + 1 for n in range(3)]?
    print(small)?
    print(list(range[u8](5, 0, -2))?)?
    fraction: f32 = 3.5
    print(fraction * 2)?
    Ok(())
[0, 4, 16, 36]
[0, 4, 16, 36]
[1, 2, 3]
[5, 3, 1]
7.0

Context guides unsuffixed literals, never changes an existing value’s type. x: u8 = 256 fails, as does assigning an i64 binding to a u8 binding. Explicit suffixes remain authoritative. A range’s bounds must fit its element type; range[u8](256) therefore fails even though its stop is exclusive.

Inference stays within straightforward expressions. It does not infer a range type backward through filters, arbitrary calls, or a previously stored range. Use explicit range[T] in those cases. There is no silent numeric widening or narrowing.