← index

Iterate

inherits Mixin · defined at core/02-iterate.qn:28

Every collection combinator, derived from a single method: each:.

A class mixes in Iterate and implements each: (call a block once per element); collect:/select:/reduce: and the rest of the vocabulary follow, along with external pull-iteration (iterator) and lazy pipelines (lazyCollect:/lazySelect:). No cursor state is kept, so iteration is re-entrant and nil is a valid element. T is the element type; U is the element type collect: produces.

Pair <- { |@a @b|
    .mix:Iterate;
    init: -> { |a b| @a = a; @b = b };
    each: -> { |blk| blk.valueWithSelfOrArg:@a; blk.valueWithSelfOrArg:@b }
};
(Pair.new:{ var a = 3; var b = 4 }).collect:{ |x| x * x }    "* -> #(9 16)
extended at core/07-statistics.qn:8

Statistics over any Iterate-able collection (List, Set, NumberRange, ...). Layered on the Iterate primitives (sum/count/sort/at:/each:), so every collection gains them. Numeric data only — applying these to non-numbers errors at the underlying arithmetic. Empty collections return nil (mean/median/variance/stddev/percentile:/mode); modes returns an empty list. Design decisions (sample vs population, interpolation, tie handling) are in docs/internal/STDLIB_NUMBERS.md. Guards use ^^ (non-local return) since they sit inside if:/else: blocks; a plain ^ would only exit the block.

Instance methods

all?:Block

True when the block answers true for every element (vacuously true when empty); stops at the first failure.

#(2 4 6).all?:{ |x| x % 2 == 0 }    "* -> true

core/02-iterate.qn:67

any?

True when there is at least one element.

#().any?    "* -> false

core/02-iterate.qn:88

any?:Block

True when the block answers true for at least one element; stops at the first match.

#(1 2 3).any?:{ |x| x > 2 }    "* -> true

core/02-iterate.qn:99

collect:Block

Transform every element through the block, into a fresh List.

#(1 2 3).collect:{ |x| x * 2 }    "* -> #(2 4 6)

core/02-iterate.qn:44

collector

The fresh, empty collection that element-preserving combinators accumulate into.

This is the species idea (GENERICS_ARCH.md 4.5): a list-shaped collector. List overrides it with .emptyLike and Set with a tag-carrying list, so select:/take:/... on a checked collection stay checked. collect: deliberately does NOT use it - its elements are whatever the block returns.

core/02-iterate.qn:37

contains?:

True when some element == item.

#(1 2 3).contains?:2    "* -> true

core/02-iterate.qn:263

count

The number of elements, counted by walking each:.

(0..5).count    "* -> 5

core/02-iterate.qn:109

count:Block

The number of elements for which the block answers true.

#(1 2 3 4).count:{ |x| x > 2 }    "* -> 2

core/02-iterate.qn:120

detect:Block

The first element for which the block answers true; nil when none matches.

#(1 2 3 4).detect:{ |x| x > 2 }    "* -> 3

core/02-iterate.qn:132

drop:

All elements after the first n. Materializes the remainder, so unlike take: it must not be used on an infinite source.

#(1 2 3 4 5).drop:2    "* -> #(3 4 5)

core/02-iterate.qn:190

fifth

The fifth element; nil if there is none.

core/02-iterate.qn:157

first

The first element; nil when empty.

core/02-iterate.qn:149

flatten

Recursively flatten nested Lists into one flat List. Only elements whose class is exactly List are descended into; any other element is kept as-is.

#(1 #(2 #(3 4)) 5).flatten    "* -> #(1 2 3 4 5)

core/02-iterate.qn:230

fourth

The fourth element; nil if there is none.

core/02-iterate.qn:155

groupBy:Block

A Map from each block-computed key to the List of elements that produced it, keys in first-seen order.

#(1 2 3 4).groupBy:{ |x| x % 2 }    "* -> #{1: #(1 3) 0: #(2 4)}

core/02-iterate.qn:242

iterator

An external (pull-style) Iterator over the elements, backed by a fiber over each:.

var it = #(10 20).iterator; it.next    "* -> 10

core/02-iterate.qn:167

join:String

Concatenate the elements' string forms (.s), with the separator between each pair.

#('a' 'b' 'c').join:', '    "* -> a, b, c

core/02-iterate.qn:439

last

The last element; nil when empty. Walks the whole iteration.

core/02-iterate.qn:159

lazyCollect:Block

Like collect:, but lazy: a Generator that transforms elements on demand instead of a materialized List, so it composes into pipelines and works on infinite sources (consume with take:).

((1..1000000).lazyCollect:{ |x| x * x }).take:3    "* -> #(1 4 9)

core/02-iterate.qn:206

lazySelect:Block

Like select:, but lazy: a Generator that filters on demand, so it composes into pipelines and works on infinite sources (consume with take:).

((1..100).lazySelect:{ |x| x % 2 == 0 }).take:2    "* -> #(2 4)

core/02-iterate.qn:218

list

Materialize the elements into a List.

(1..4).list    "* -> #(1 2 3)

core/02-iterate.qn:478

max

The largest element by >; nil when empty.

#(3 1 4).max    "* -> 4

core/02-iterate.qn:353

max:Block

The element the block ranks highest; nil when empty.

The block receives (currentBest candidate) and answers true when currentBest outranks the candidate - a >-style comparison, the same block shape min: takes.

#(-5 2 3).max:{ |a b| a.abs > b.abs }    "* -> -5

core/02-iterate.qn:340

mean

Arithmetic mean. Forces Double division so integer inputs don't truncate.

#(1 2 3 4).mean    "* -> 2.5
#(1 2).mean        "* -> 1.5

core/07-statistics.qn:15

median

Middle of the sorted data: the exact element for an odd count, the average of the two central elements (a Double) for an even count.

#(3 1 2).median      "* -> 2
#(1 2 3 4).median    "* -> 2.5

core/07-statistics.qn:28

min

The smallest element by >; nil when empty.

#(3 1 4).min    "* -> 1

core/02-iterate.qn:376

min:Block

The element the block ranks lowest; nil when empty.

Takes the same >-style (currentBest candidate) comparison block as max:, and keeps the element it ranks lowest.

#(-5 2 3).min:{ |a b| a.abs > b.abs }    "* -> 2

core/02-iterate.qn:363

mode

The single most frequent value; on a tie, the first one encountered. nil if empty.

#(1 2 2 3 3).mode    "* -> 2

core/07-statistics.qn:105

modes

Every maximally-frequent value, in first-encountered order (a list; empty if no data). Use this when the data may be multimodal; mode is the single-value shortcut. Values are keyed by their string form, so == values (e.g. 1 and 1.0) are counted together.

#(1 2 2 3 3).modes    "* -> #(2 3)

core/07-statistics.qn:114

none?:Block

True when the block answers true for no element; stops at the first match.

#(1 3 5).none?:{ |x| x % 2 == 0 }    "* -> true

core/02-iterate.qn:78

nth:

The element at zero-based position n; nil when out of range.

#(10 20 30).nth:1    "* -> 20

core/02-iterate.qn:142

partition:Block

Split into two collections: the elements for which the block answers true, then the rest, as a two-element List.

#(1 2 3 4).partition:{ |x| x % 2 == 0 }    "* -> #(#(2 4) #(1 3))

core/02-iterate.qn:384

percentile:

The p-th percentile (p in 0..100) by linear interpolation between the two closest ranks, so percentile:50 == median, percentile:0 == min, percentile:100 == max. nil if empty.

#(1 2 3 4).percentile:25    "* -> 1.75

core/07-statistics.qn:85

populationStddev

Population standard deviation: the sqrt of populationVariance (n denominator). nil if empty.

#(1 2 3 4).populationStddev    "* -> 1.118033988749895

core/07-statistics.qn:73

populationVariance

Population variance — divides by n. Use when the data *is* the whole population.

core/07-statistics.qn:48

reduce:Block

Seedless fold: combine the elements pairwise with the block, seeding the accumulator with the FIRST element; nil when empty.

The fold starts from the second element (BUGS.md Finding 9 - the old version seeded with the block result's class default and folded the first element against it, which is only correct when the default is a left identity: + and concat survived, */-/min-style folds returned garbage). A seeded flag, not sum.defined?, so nil elements fold correctly too.

#(1 2 3 4).reduce:{ |a b| a * b }    "* -> 24

core/02-iterate.qn:281

reduce:Block into:

Fold the elements into an explicit starting accumulator: the block receives (accumulator element) and answers the new accumulator.

#(1 2 3).reduce:{ |acc x| acc + x } into:100    "* -> 106

core/02-iterate.qn:300

reject:Block

The elements for which the block answers false - select:'s complement.

#(1 2 3 4).reject:{ |x| x % 2 == 0 }    "* -> #(1 3)

core/02-iterate.qn:402

reverse

The elements in reverse order.

#(1 2 3).reverse    "* -> #(3 2 1)

core/02-iterate.qn:453

second

The second element; nil if there is none.

core/02-iterate.qn:151

select:Block

The elements for which the block answers true, in order.

#(1 2 3 4).select:{ |x| x % 2 == 0 }    "* -> #(2 4)

core/02-iterate.qn:55

sort

The elements sorted ascending.

#(3 1 2).sort    "* -> #(1 2 3)

core/02-iterate.qn:471

sort:Block

The elements sorted by a two-argument precedes-block (true means the first argument sorts earlier).

#(3 1 2).sort:{ |a b| a > b }    "* -> #(3 2 1)

core/02-iterate.qn:465

stddev

Sample standard deviation: the sqrt of variance (n-1 denominator). nil for fewer than two elements.

#(1 2 3 4).stddev    "* -> 1.2909944487358056

core/07-statistics.qn:61

sum

The sum of the elements via +; nil when empty. Works for any element type with a class default zero - e.g. Strings concatenate.

#(1 2 3).sum    "* -> 6

core/02-iterate.qn:312

sum:Block

The sum (via +) of the block's results over the elements; nil when empty. Seeded with the class default of the first result, so any result type with a default and + works.

#(1 2 3).sum:{ |x| x * x }    "* -> 14

core/02-iterate.qn:321

take:

The first n elements, fewer when the iteration is shorter. Pulls through an iterator, so it is safe on infinite sources such as generators.

(1..100).take:3    "* -> #(1 2 3)

core/02-iterate.qn:176

third

The third element; nil if there is none.

core/02-iterate.qn:153

uniq

The distinct elements (by ==), keeping first-seen order.

#(1 2 1 3 2).uniq    "* -> #(1 2 3)

core/02-iterate.qn:413

variance

Sample variance — divides by n-1 (Bessel's correction), the right default when the data is a sample of something larger. nil for fewer than two elements (undefined).

core/07-statistics.qn:40

zip:

Pair up with another iterable, element by element, stopping at the shorter: a List of two-element Lists.

#(1 2 3).zip:#(10 20)    "* -> #(#(1 10) #(2 20))

core/02-iterate.qn:425