Implement TCO for cons cell toString

This commit is contained in:
Mike Cifelli 2017-11-12 16:40:49 -05:00
parent e8e9d2e12d
commit efb0329fda
3 changed files with 26 additions and 8 deletions

View File

@ -0,0 +1,11 @@
(load "../lang/functions.lisp")
(defun build (n lst)
(if (= n 0) lst
(build (- n 1) (cons (car lst) lst))))
(defun build2 (n lst)
(if (= n 0) lst
(build2 (- n 1) (build 200 lst))))
(length (build2 200 (build2 200 (build2 200 (build2 200 '(1 1 1 1 0 0 0 0))))))

View File

@ -8,4 +8,4 @@
(if (= n 0) lst (if (= n 0) lst
(build2 (- n 1) (build 200 lst)))) (build2 (- n 1) (build 200 lst))))
(length (build2 200 (build2 200 '(1 1 1 1 0 0 0 0)))) (build2 200 (build2 200 (build2 200 (build2 200 '(1 1 1 1 0 0 0 0)))))

View File

@ -1,5 +1,10 @@
package sexpression; package sexpression;
import static recursion.tail.TailCalls.done;
import static recursion.tail.TailCalls.tailCall;
import recursion.tail.TailCall;
@DisplayName("list") @DisplayName("list")
public class Cons extends SExpression { public class Cons extends SExpression {
@ -34,16 +39,18 @@ public class Cons extends SExpression {
@Override @Override
public String toString() { public String toString() {
return ("(" + toStringAux()); return toStringTailRecursive("(").invoke();
} }
private String toStringAux() { private TailCall<String> toStringTailRecursive(String precedingString) {
String leadingString = precedingString + first.toString();
if (rest.isNull()) if (rest.isNull())
return (first.toString() + ")"); return done(leadingString + ")");
else if (rest.isCons()) else if (rest.isCons())
return (first.toString() + " " + ((Cons) rest).toStringAux()); return tailCall(() -> ((Cons) rest).toStringTailRecursive(leadingString + " "));
return (first.toString() + " . " + rest.toString() + ")"); return done(leadingString + " . " + rest.toString() + ")");
} }
} }