Functions and Closures in Clump

In this tutorial we illustrate the closure mechanism. In fact like any entity in the language a function is a first class object. It means such kind of object can be viewed by a class. Then based on this approach a function can also be linked to a given set of behaviors provided by classes.

The array creation can be provided with a more expressive syntax using function as shown in the next code sample.

class multiArraysInline(System) implements Main {
    start(args) {
        int[][] multi = 
            new int[][10](int[] (int d) { return new int[d+1](d); });

        for(int[] line : multi) {           
            for(int element : line) {
                this.stdout().print(element.toString() + " ");
            }
            this.stdout().println();
        }
    }
}
The most important in this example is the capability to create a closure with int[] (int d) { return new int[d+1](d); }. Indeed since Clump is a strong typed language such closure provides both a specification and an implementation.

The previous example defines an anonymous function and then is defined and used only once. Indeed such function can be linked to a variable. In this case it can be reused like any variable anytime it's required in the program.

class multiArrays(System) implements Main {
    start(args) {
        {int[] (int)} makeLine = int[] (int column) {
            return new int[column+1](column);
        };
        int[][] multi = new int[][10](makeLine);
        for(int[] line : multi) {           
            for(int element : line) {
                this.stdout().print(element.toString() + " ");
            }
            this.stdout().println();
        }
    }
}
Such function referenced by a variable can be specified in a more natural way as illustrated in the next example.
class multiArrays(System) implements Main {
    start(args) {
        int[] makeLine(int column) {
            return new int[column+1](column);
        };
        int[][] multi = new int[][10](makeLine);
        for(int[] line : multi) {           
            for(int element : line) {
                this.stdout().print(element.toString() + " ");
            }
            this.stdout().println();
        }
    }
}
Since package variables are equivalent to any variable except the scope such variable can also be function. In this case the previous example can also specified as shown in the next example.
int[] makeLine(int column) {
    return new int[column+1](column);
};

class multiArrays(System) implements Main {
    start(args) {
        int[][] multi = new int[][10](makeLine);
        for(int[] line : multi) {           
            for(int element : line) {
                this.stdout().print(element.toString() + " ");
            }
            this.stdout().println();
        }
    }
}
In this case this variable does en enclose any variable but it's accessible from everywhere. Indeed such accessibility can be managed using private declaration.

The previous example can be designed with a class protected method.

class multiArrays(System) implements Main, ILineMaker {
    int[] makeLine(int column) {
        return new int[column+1](column);
    }

    start(args) {
        int[][] multi = new int[][10](makeLine);
        for(int[] line : multi) {           
            for(int element : line) {
                this.stdout().print(element.toString() + " ");
            }
            this.stdout().println();
        }
    }
}

In Clump Functions are objects but this concept hides in fact the closure mechanism. A closure was a function and a dedicated environment referencing variables. In such context programs can be dynamically created based on functionnal expression creation. This aspect is illustrated in the next example.

object NotFound {}

type Binder<K,V> = {V (K) throws NotFound}

interface IBinder<K,V> {
    void set(K, V);
    V get(K) throws NotFound;
}

class binder<K extends Equivalent<K>,V>(Binder<K,V>) implements IBinder<K,V> {
    set(key,value) {
        this = V (K j) throws NotFound { 
            if key == j {
                return value;
            } else {
                return this(j);
            }
        };
    }

    get(i) {
        return this(i);
    }
}



    Last modified: Tue Oct 23 05:49:42 CEST 2012