for
for transforms a source sequence into a new sequence by evaluating the body per element. See nx-grammar.md for formal syntax.
Value Form
Section titled “Value Form”type Image = { url:string title:string }
let gallery(images:Image+) = { for image in images { <img src={image.url} alt={image.title}/> }}forreturns a sequence.- The loop variable is scoped to the body.
Item + Index Form
Section titled “Item + Index Form”type Item = { label:string }
let stripedRows(rows:Item+) = { for row, index in rows { <tr className={if (index % 2 == 0) { "even" } else { "odd" }}> <td>{row.label}</td> </tr> }}- The item comes first; the optional second identifier receives its zero-based index.
- Use this form when you need stable keys or different styling per position.
Counting with a range
Section titled “Counting with a range”for also iterates a range, so counting needs no list:
let squares = { for i in 0..4 { i * i } } // 0 1 4 9let pages = { for page in 1..=3 { page } } // 1 2 3let <Stars count:int /> = { for i in 0..count { <Star /> } }a..bcounts fromaup to but excludingb;a..=bincludesb. Both build the built-inRangetype.- The item is each integer in turn, at the range’s own integer type, and the optional index counts from zero as it does over a list.
- An empty or reversed range yields nothing:
0..0,5..2and1..=0each produce no items. - Only a range of an integer type —
int,int32orint64— iterates.for x in 0..2.5is a type error rather than a guessed step. - The range is never turned into a list first, so
for i in 0..ncosts one body evaluation per item and nothing else.
A range value from anywhere iterates, not only one written with the operators:
let span:<Range T=int/> = <Range T=int start={2} end={4} endInclusive={true} />let items = { for i in span { i } } // 2 3 4Filtering While Iterating
Section titled “Filtering While Iterating”Because if is also an expression, you can yield optional values inside the loop. Returning nothing from a branch omits that item.
type Person = { name:string age:int }
let adults(people:Person+) = { for person in people { if person.age >= 18 { person } }}Nested Loops
Section titled “Nested Loops”Compose loops by nesting for expressions without reaching for imperative constructs. A sequence
never holds another sequence, so a grid is a sequence of records that each hold a row’s cells:
type GridRow = { cells:int+ }
let cells(grid:GridRow+) = { for row in grid { for cell in row.cells { <Cell value={cell}/> } }}The result is flat: each inner for contributes its items to the outer one’s sequence.
See also
Section titled “See also”- Language Tour: Expressions & Control Flow
- Reference: if
- Grammar: nx-grammar.md – Elements/for