6.2. Functional programming library

The FUNCTIONAL module implements lazy iterator adapters and higher-order function utilities including filter, map, reduce, fold, scan, flatten, flat_map, enumerate, chain, pairwise, iterate, islice, cycle, repeat, sorted, sum, any, all, tap, for_each, find, find_index, and partition.

See Functional Programming for a hands-on tutorial.

All functions and symbols are in “functional” module, use require to get access to it.

require daslib/functional

Example:

require daslib/functional

    [export]
    def main() {
        var src <- [iterator for (x in range(6)); x]
        var evens <- filter(src, @(x : int) : bool { return x % 2 == 0; })
        for (v in evens) {
            print("{v} ")
        }
        print("\n")
    }
    // output:
    // 0 2 4

6.2.1. Transformations

6.2.1.1. filter

functional::filter(src: iterator<auto(TT)>; blk: function<(what:TT):bool>) : auto()

iterates over src and yields only those elements for which blk returns true

Arguments
  • src : iterator<auto(TT)>

  • blk : function<(what:TT):bool>

functional::filter(src: iterator<auto(TT)>; blk: lambda<(what:TT):bool>) : auto()

6.2.1.2. flat_map

functional::flat_map(src: iterator<auto(TT)>; blk: lambda<(what:TT):auto(QQ)>) : auto()

maps each element to an iterator, then flattens the results one level

Arguments
  • src : iterator<auto(TT)>

  • blk : lambda<(what:TT):auto(QQ)>

functional::flat_map(src: iterator<auto(TT)>; blk: function<(what:TT):auto(QQ)>) : auto()

functional::flatten(it: iterator<auto(TT)>) : auto()

iterates over it, then iterates over each element of each element of it and yields it

Arguments
  • it : iterator<auto(TT)>

6.2.1.3. map

functional::map(src: iterator<auto(TT)>; blk: function<(what:TT):auto(QQ)>) : auto()

iterates over src and yields the result of blk for each element

Arguments
  • src : iterator<auto(TT)>

  • blk : function<(what:TT):auto(QQ)>

functional::map(src: iterator<auto(TT)>; blk: lambda<(what:TT):auto(QQ)>) : auto()

6.2.1.4. scan

functional::scan(src: iterator<auto(TT)>; seed: auto(AGG); blk: function<(acc:AGG;x:TT):AGG>) : auto()

yields every intermediate accumulator value, starting from seed

Arguments
  • src : iterator<auto(TT)>

  • seed : auto(AGG)

  • blk : function<(acc:AGG;x:TT):AGG>

functional::scan(src: iterator<auto(TT)>; seed: auto(AGG); blk: lambda<(acc:AGG;x:TT):AGG>) : auto()

6.2.1.5. sorted

functional::sorted(it: iterator<auto(TT)>) : auto()

iterates over input and returns it sorted version

Arguments
  • it : iterator<auto(TT)>

functional::sorted(arr: array<auto>) : auto()

6.2.2. Aggregation

6.2.2.1. all

functional::all(it: iterator<auto(TT)>) : auto()

iterates over it and yields true if all elements are true

Arguments
  • it : iterator<auto(TT)>

functional::all(it: auto) : auto()

6.2.2.2. any

functional::any(it: auto) : auto()

iterates over it and yields true if any element is true

Arguments
  • it : auto

functional::any(it: iterator<auto(TT)>) : auto()

6.2.2.3. fold

functional::fold(it: iterator<auto(TT)>; seed: auto(AGG); blk: lambda<(acc:AGG;x:TT):AGG>) : auto()

combines elements left-to-right starting from seed

Arguments
  • it : iterator<auto(TT)>

  • seed : auto(AGG)

  • blk : lambda<(acc:AGG;x:TT):AGG>

functional::fold(it: iterator<auto(TT)>; seed: auto(AGG); blk: block<(acc:AGG;x:TT):AGG>) : auto()
functional::fold(it: iterator<auto(TT)>; seed: auto(AGG); blk: function<(acc:AGG;x:TT):AGG>) : auto()

6.2.2.4. reduce

functional::reduce(it: iterator<auto(TT)>; blk: function<(left:TT;right:TT):TT>) : auto()

iterates over it and yields the reduced (combined) result of blk for each element and previous reduction result

Arguments
  • it : iterator<auto(TT)>

  • blk : function<(left:TT;right:TT):TT>

functional::reduce(it: iterator<auto(TT)>; blk: lambda<(left:TT;right:TT):TT>) : auto()
functional::reduce(it: iterator<auto(TT)>; blk: block<(left:TT;right:TT):TT>) : auto()

6.2.2.5. reduce_or_default

functional::reduce_or_default(it: iterator<auto(TT)>; blk: function<(left:TT;right:TT):TT>; default_value: TT) : auto()

like reduce, but returns default_value on empty input

Arguments
  • it : iterator<auto(TT)>

  • blk : function<(left:TT;right:TT):TT>

  • default_value : TT

functional::reduce_or_default(it: iterator<auto(TT)>; default_value: TT; blk: block<(left:TT;right:TT):TT>) : auto()
functional::reduce_or_default(it: iterator<auto(TT)>; blk: lambda<(left:TT;right:TT):TT>; default_value: TT) : auto()

functional::sum(it: iterator<auto(TT)>) : auto()

iterates over it and yields the sum of all elements same as reduce(it, @(a,b) => a + b)

Arguments
  • it : iterator<auto(TT)>

6.2.3. Search and split

6.2.3.1. find

functional::find(src: iterator<auto(TT)>; blk: function<(what:TT):bool>; default_value: TT) : auto()

returns the first element for which blk returns true, or default_value

Arguments
  • src : iterator<auto(TT)>

  • blk : function<(what:TT):bool>

  • default_value : TT

functional::find(src: iterator<auto(TT)>; blk: lambda<(what:TT):bool>; default_value: TT) : auto()
functional::find(src: iterator<auto(TT)>; default_value: TT; blk: block<(what:TT):bool>) : auto()

6.2.3.2. find_index

functional::find_index(src: iterator<auto(TT)>; blk: lambda<(what:TT):bool>) : int()

returns the index of the first element for which blk returns true, or -1

Arguments
  • src : iterator<auto(TT)>

  • blk : lambda<(what:TT):bool>

functional::find_index(src: iterator<auto(TT)>; blk: block<(what:TT):bool>) : int()
functional::find_index(src: iterator<auto(TT)>; blk: function<(what:TT):bool>) : int()

6.2.3.3. partition

functional::partition(src: iterator<auto(TT)>; blk: lambda<(what:TT):bool>) : tuple<array<TT>;array<TT>>()

splits elements into (matching, non_matching) arrays

Arguments
  • src : iterator<auto(TT)>

  • blk : lambda<(what:TT):bool>

functional::partition(src: iterator<auto(TT)>; blk: function<(what:TT):bool>) : tuple<array<TT>;array<TT>>()
functional::partition(src: iterator<auto(TT)>; blk: block<(what:TT):bool>) : tuple<array<TT>;array<TT>>()

6.2.4. Iteration

functional::echo(x: auto; extra: string = "\n") : auto()

prints x to the output with extra appended, then returns x unchanged. Non-destructive — safe to use in expression chains.

Arguments
  • x : auto

  • extra : string

functional::enumerate(src: iterator<auto(TT)>) : auto()

yields tuples of (index, element) for each element in src

Arguments
  • src : iterator<auto(TT)>

6.2.4.1. for_each

functional::for_each(src: iterator<auto(TT)>; blk: function<(what:TT):void>) : auto()

invokes blk on every element of src

Arguments
  • src : iterator<auto(TT)>

  • blk : function<(what:TT):void>

functional::for_each(src: iterator<auto(TT)>; blk: lambda<(what:TT):void>) : auto()
functional::for_each(src: iterator<auto(TT)>; blk: block<(what:TT):void>) : auto()

6.2.4.2. tap

functional::tap(src: iterator<auto(TT)>; blk: function<(what:TT):void>) : auto()

yields every element unchanged, calling blk on each as a side-effect

Arguments
  • src : iterator<auto(TT)>

  • blk : function<(what:TT):void>

functional::tap(src: iterator<auto(TT)>; blk: lambda<(what:TT):void>) : auto()

6.2.5. Generators

functional::chain(a: iterator<auto(TT)>; b: iterator<auto(TT)>) : auto()

yields all elements of a, then all elements of b

Arguments
  • a : iterator<auto(TT)>

  • b : iterator<auto(TT)>

functional::cycle(src: iterator<auto(TT)>) : auto()

endlessly iterates over src

Arguments
  • src : iterator<auto(TT)>

functional::islice(src: iterator<auto(TT)>; start: int; stop: int) : auto()

iterates over src and yields only the elements in the range [start,stop)

Arguments
  • src : iterator<auto(TT)>

  • start : int

  • stop : int

6.2.5.1. iterate

functional::iterate(seed: auto(TT); blk: function<(what:TT):TT>) : auto()

yields seed, f(seed), f(f(seed)), … infinitely.

Arguments
  • seed : auto(TT)

  • blk : function<(what:TT):TT>

functional::iterate(seed: auto(TT); blk: lambda<(what:TT):TT>) : auto()

functional::pairwise(src: iterator<auto(TT)>) : auto()

yields consecutive pairs: (a,b), (b,c), (c,d), …

Arguments
  • src : iterator<auto(TT)>

functional::repeat(value: auto(TT); count: int = -(1)) : auto()

yields value count times. If count is negative, repeats forever.

Arguments
  • value : auto(TT)

  • count : int

functional::repeat_ref(value: auto(TT); total: int) : auto()

yields value by reference count times

Arguments
  • value : auto(TT)

  • total : int

6.2.6. Predicates

functional::is_equal(a: auto; b: auto) : auto()

yields true if a and b are equal

Arguments
  • a : auto

  • b : auto

functional::is_not_equal(a: auto; b: auto) : auto()

yields true if a and b are not equal

Arguments
  • a : auto

  • b : auto

functional::not(x: auto) : auto()

yields !x

Arguments
  • x : auto