This module imlements operations for iterators and slices. You can see it as a lazy version of sequtils.
The iterators can easily be combined:
for i in filter(map(filter(2..10, proc(x: int): bool = x mod 2 == 0), proc(x: int): int = x * 2), proc(x: int): bool = x mod 8 == 0): echo i var s = toSeq (2..10).filter(proc(x): bool = x mod 2 == 0). map(proc(x): int = x * 2).filter(proc(x): bool = x mod 8 == 0) echo s var a = (2..10).filter(proc(x: int): bool = x mod 2 == 0) var b = a.map((x: int) => x * 2) for i in b.map((x: int) => x + 2): echo i
Performance example:
Raw implementation with a loop:
# 0.2 s for i in 1..100_000_000: if i mod 2 == 0: if i mod 4 == 0: if i mod 8 == 0: if i mod 16000 == 0: echo i div 16
Using sequtils:
# 5.3 s for i in toSeq(1..100_000_000). filter(proc(x): bool = x mod 2 == 0). filter(proc(x): bool = x mod 4 == 0). filter(proc(x): bool = x mod 8 == 0). filter(proc(x): bool = x mod 16000 == 0). map(proc(x): int = x div 16): echo i
Using iterutils:
# 1.8 s for i in (1..100_000_000). filter(proc(x): bool = x mod 2 == 0). filter(proc(x): bool = x mod 4 == 0). filter(proc(x): bool = x mod 8 == 0). filter(proc(x): bool = x mod 16000 == 0). map(proc(x): int = x div 16): echo i
Types
Iterable*[T] = (iterator (): T) | Slice[T]
- Everything that can be iterated over, iterators and slices so far. Source
Procs
proc toIter*[T](s: Slice[T]): iterator (): T
- Iterate over a slice. Source
proc toIter*[T](i: iterator (): T): iterator (): T
- Nop Source
proc map*[T, S](i: Iterable[T]; f: proc (x: T): S): iterator (): S
-
Returns an iterator which applies f to every item in i.
for x in map(2..10, proc(x): int = x * 2): echo x for i in (1..10).map(proc(x): string = "foo: " & $x): echo i
Source proc filter*[T](i: Iterable[T]; f: proc (x: T): bool): iterator (): T
-
Iterates through an iterator and yields every item that fulfills the predicate f.
for x in filter(1..11, proc(x): bool = x mod 2 == 0): echo x
Source proc concat*[T](its: varargs[T, toIter]): iterator (): T
-
Takes several iterators' items and returns a new iterator from them.
for i in concat(1..4, 20..23): echo i
Source proc zip*[T, S](i: (iterator (): T) | Slice[T]; j: Iterable[S]): iterator (): tuple[ a: T, b: S]
-
Iterates through both iterators at the same time, returning a tuple of both elements as long as neither of the iterators has finished.
for x in zip(1..4, 20..24): echo x
Source proc slice*[T](i: Iterable[T]; first = 0; last = 0; step = 1): iterator (): T
-
Yields every step item in i from index first to last.
for i in slice(0..100, 10, 20) echo i
Source proc delete*[T](i: Iterable[T]; first = 0; last = 0): iterator (): T
-
Yields the items in i except for the ones between first and last.
for x in delete(1..10, 4, 8): echo x
Source proc foldl*[T, S](i: Iterable[T]; f: proc (x: S; y: T): S; y: S): S
-
Folds the values as the iterator yields them, returning the accumulation.
As the initial value of the accumulation y is used.
echo foldl(1..10, proc(x,y: int): int = x + y, 0)
Source proc foldl*[T](i: Iterable[T]; f: proc (x, y: T): T): T
-
Folds the values as the iterator yields them, returning the accumulation.
The iterator is required to return at least a single element.
echo foldl(1..10, proc(x,y: int): int = x + y)
Source
Iterators
iterator revItems*(a)
- Source
iterator revPairs*(a)
-
iterates over the items of a seq, array or string in reverse, yielding (index, a[index]).
Sourcevar xs = @[1,3,5,7,9,11]
- for i,x in xs.revPairs:
- echo i, " ", x
iterator map*[T, S](i: Iterable[T]; f: proc (x: T): S): S
- Source
iterator filter*[T](i: Iterable[T]; f: proc (x: T): bool): T
- Source
iterator concat*[T](its: varargs[T, toIter]): auto
- Source
iterator zip*[T, S](i: (iterator (): T) | Slice[T]; j: Iterable[S]): tuple[a: T, b: S]
- Source
iterator slice*[T](i: Iterable[T]; first = 0; last = 0; step = 1): T
- Source
iterator delete*[T](i: Iterable[T]; first = 0; last = 0): T
- Source