// The factoral function in continuation-passing style, in Java // sestoft@dina.kvl.dk 2002-04-03, 2003-03-19 // A Cont object is a continuation: it has a method k that given the // result of a subcomputation will return the final result: interface Cont { int k(int v); } // Calling the two versions of factorial: class Factorial { public static void main(String[] args) { int n = Integer.parseInt(args[0]); System.out.println(facc(n, new Cont() { public int k(int v) { return v; } })); System.out.println(faci(n, new Cont() { public int k(int v) { return v; } })); } // A continuation-passing version of factorial. This is a straight // translation of the Standard ML version: static int facc(final int n, final Cont cont) { if (n == 0) return cont.k(1); else return facc(n-1, new Cont() { public int k(int v) { return cont.k(n * v); } }); } // Another continuation-passing version of factorial. Since facc // above is tail-recursive, it can be rewritten as a loop. This // shows how it builds up a continuation and finally applies it: static int faci(int n, Cont cont) { while (n != 0) { cont = new FacCont(n, cont); n--; } return cont.k(1); } } // Auxiliary class to implement faci. Needed for Java-technical // reasons; a local inner class can refer only to `final' variables in // the enclosing method, but faci must update the cont variable in the // loop. class FacCont implements Cont { private final int n; private final Cont cont; public FacCont(int n, Cont cont) { this.n = n; this.cont = cont; } public int k(int v) { return cont.k(n * v); } }