Add ability to read large lists
This commit is contained in:
parent
a9c13610a2
commit
1fbc74f3ac
|
@ -1,4 +1,4 @@
|
||||||
|TranscendentalLisp.Recursion||17:56:26 Sat, Nov 18, 2017|
|
|TranscendentalLisp.Recursion||10:47:58 Sun, Nov 19, 2017|
|
||||||
|TranscendentalLisp||16:15:14 Fri, Mar 17, 2017|
|
|TranscendentalLisp||16:15:14 Fri, Mar 17, 2017|
|
||||||
|TranscendentalLisp.Macros||10:10:15 Mon, Mar 13, 2017|
|
|TranscendentalLisp.Macros||10:10:15 Mon, Mar 13, 2017|
|
||||||
|TranscendentalLisp.MacroTests||10:07:00 Mon, Mar 13, 2017|
|
|TranscendentalLisp.MacroTests||10:07:00 Mon, Mar 13, 2017|
|
||||||
|
|
|
@ -4,8 +4,9 @@ Test
|
||||||
Test recursion capabilities of various functions.
|
Test recursion capabilities of various functions.
|
||||||
|
|
||||||
| script | lisp interpreter fixture |
|
| script | lisp interpreter fixture |
|
||||||
|
| show | evaluate text | (load "lisp/random/big-list.lisp") |
|
||||||
| show | evaluate text | (load "lisp/random/list-builder.lisp") |
|
| show | evaluate text | (load "lisp/random/list-builder.lisp") |
|
||||||
| check | evaluate text | (setq big-list (list-doubler '(1 1 1 1 1 1 1 1) 11)) | =~/1\)$/ |
|
| check | evaluate text | big-list | =~/1\)$/ |
|
||||||
| check | evaluate text | (length big-list) | 16384 |
|
| check | evaluate text | (length big-list) | 16384 |
|
||||||
| check | evaluate text | (length (apply 'list big-list)) | 16384 |
|
| check | evaluate text | (length (apply 'list big-list)) | 16384 |
|
||||||
| check | evaluate text | (apply '/ big-list) | 1 |
|
| check | evaluate text | (apply '/ big-list) | 1 |
|
||||||
|
@ -14,4 +15,4 @@ Test recursion capabilities of various functions.
|
||||||
| check | evaluate text | (apply '- big-list) | -16382 |
|
| check | evaluate text | (apply '- big-list) | -16382 |
|
||||||
| check | evaluate text | (apply '= big-list) | T |
|
| check | evaluate text | (apply '= big-list) | T |
|
||||||
| check | evaluate text | (apply '> (decreasing-list 0 10000)) | T |
|
| check | evaluate text | (apply '> (decreasing-list 0 10000)) | T |
|
||||||
| check | evaluate text | (apply '< (increasing-list 10000 10000)) | T |
|
| check | evaluate text | (apply '< (increasing-list 10000 10000)) | T |
|
File diff suppressed because one or more lines are too long
|
@ -1,11 +1,13 @@
|
||||||
package token;
|
package token;
|
||||||
|
|
||||||
import static sexpression.Nil.NIL;
|
import static recursion.TailCalls.done;
|
||||||
|
|
||||||
import java.util.function.Supplier;
|
import java.util.function.Supplier;
|
||||||
|
|
||||||
import error.LineColumnException;
|
import error.LineColumnException;
|
||||||
import file.FilePosition;
|
import file.FilePosition;
|
||||||
|
import recursion.TailCall;
|
||||||
|
import sexpression.Cons;
|
||||||
import sexpression.SExpression;
|
import sexpression.SExpression;
|
||||||
|
|
||||||
public class RightParenthesis extends Token {
|
public class RightParenthesis extends Token {
|
||||||
|
@ -20,8 +22,8 @@ public class RightParenthesis extends Token {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public SExpression parseSExpressionTail(Supplier<Token> getNextToken) {
|
public TailCall<SExpression> parseListBackwards(Cons accumulator, Supplier<Token> getNextToken) {
|
||||||
return NIL;
|
return done(accumulator);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class StartsWithRightParenthesisException extends LineColumnException {
|
public static class StartsWithRightParenthesisException extends LineColumnException {
|
||||||
|
|
|
@ -1,8 +1,13 @@
|
||||||
package token;
|
package token;
|
||||||
|
|
||||||
|
import static recursion.TailCalls.done;
|
||||||
|
import static recursion.TailCalls.tailCall;
|
||||||
|
import static sexpression.Nil.NIL;
|
||||||
|
|
||||||
import java.util.function.Supplier;
|
import java.util.function.Supplier;
|
||||||
|
|
||||||
import file.FilePosition;
|
import file.FilePosition;
|
||||||
|
import recursion.TailCall;
|
||||||
import sexpression.Cons;
|
import sexpression.Cons;
|
||||||
import sexpression.SExpression;
|
import sexpression.SExpression;
|
||||||
|
|
||||||
|
@ -24,19 +29,38 @@ public abstract class Token {
|
||||||
return position;
|
return position;
|
||||||
}
|
}
|
||||||
|
|
||||||
// s-expression ::= NUMBER | IDENTIFIER | STRING | QUOTE_MARK s-expression | LEFT_PAREN
|
// --------------------------------------------------------------------------------------------
|
||||||
|
// s-expression
|
||||||
|
// ::= NUMBER | IDENTIFIER | STRING | QUOTE_MARK s-expression | LEFT_PAREN s-expression-tail
|
||||||
|
//
|
||||||
// s-expression-tail
|
// s-expression-tail
|
||||||
// s-expression-tail ::= RIGHT_PAREN | s-expression s-expression-tail
|
// ::= RIGHT_PAREN | s-expression s-expression-tail
|
||||||
|
// --------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
public abstract SExpression parseSExpression(Supplier<Token> getNextToken);
|
public abstract SExpression parseSExpression(Supplier<Token> getNextToken);
|
||||||
|
|
||||||
public SExpression parseSExpressionTail(Supplier<Token> getNextToken) {
|
public SExpression parseSExpressionTail(Supplier<Token> getNextToken) {
|
||||||
SExpression first = parseSExpression(getNextToken);
|
Cons list = (Cons) parseListBackwards(NIL, getNextToken).invoke();
|
||||||
|
|
||||||
Token nextToken = getNextToken.get();
|
return reverse(NIL, list).invoke();
|
||||||
SExpression rest = nextToken.parseSExpressionTail(getNextToken);
|
}
|
||||||
|
|
||||||
return new Cons(first, rest);
|
public TailCall<SExpression> parseListBackwards(Cons accumulator, Supplier<Token> getNextToken) {
|
||||||
|
Cons nextAccumulator = new Cons(parseSExpression(getNextToken), accumulator);
|
||||||
|
Token next = getNextToken.get();
|
||||||
|
|
||||||
|
return tailCall(() -> next.parseListBackwards(nextAccumulator, getNextToken));
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO - refactor into a built in function?
|
||||||
|
private TailCall<SExpression> reverse(Cons accumulator, Cons list) {
|
||||||
|
if (list.isNull())
|
||||||
|
return done(accumulator);
|
||||||
|
|
||||||
|
Cons nextAccumulator = new Cons(list.getFirst(), accumulator);
|
||||||
|
Cons rest = (Cons) list.getRest();
|
||||||
|
|
||||||
|
return tailCall(() -> reverse(nextAccumulator, rest));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue