diff options
Diffstat (limited to 'JPratt/src/main/java/bjc/pratt/commands')
21 files changed, 246 insertions, 80 deletions
diff --git a/JPratt/src/main/java/bjc/pratt/commands/AbstractInitialCommand.java b/JPratt/src/main/java/bjc/pratt/commands/AbstractInitialCommand.java index 50e884b..48f9ba7 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/AbstractInitialCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/AbstractInitialCommand.java @@ -21,7 +21,7 @@ import bjc.utils.parserutils.ParserException; */ public abstract class AbstractInitialCommand<K, V, C> implements InitialCommand<K, V, C> { @Override - public Tree<Token<K, V>> denote(final Token<K, V> operator, + public CommandResult<K, V> denote(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { return intNullDenotation(operator, ctx); } @@ -39,7 +39,7 @@ public abstract class AbstractInitialCommand<K, V, C> implements InitialCommand< * @throws ParserException * If something went wrong while parsing. */ - protected abstract Tree<Token<K, V>> intNullDenotation(Token<K, V> operator, + protected abstract CommandResult<K, V> intNullDenotation(Token<K, V> operator, ParserContext<K, V, C> ctx) throws ParserException; }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/BinaryCommand.java b/JPratt/src/main/java/bjc/pratt/commands/BinaryCommand.java index 069de78..7a65052 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/BinaryCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/BinaryCommand.java @@ -1,6 +1,7 @@ package bjc.pratt.commands; import bjc.pratt.ParserContext; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -39,12 +40,14 @@ public abstract class BinaryCommand<K, V, C> extends BinaryPostCommand<K, V, C> protected abstract int rightBinding(); @Override - public Tree<Token<K, V>> denote(final Tree<Token<K, V>> operand, + public CommandResult<K, V> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - final Tree<Token<K, V>> opr + final CommandResult<K,V> opr = ctx.parse.parseExpression(rightBinding(), ctx.tokens, ctx.state, false); + + if (opr.status != Status.SUCCESS) return opr; - return new SimpleTree<>(operator, operand, opr); + return CommandResult.success(new SimpleTree<>(operator, operand, opr.success())); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/CommandResult.java b/JPratt/src/main/java/bjc/pratt/commands/CommandResult.java new file mode 100644 index 0000000..d27400f --- /dev/null +++ b/JPratt/src/main/java/bjc/pratt/commands/CommandResult.java @@ -0,0 +1,97 @@ +package bjc.pratt.commands; + +import bjc.data.Tree; +import bjc.pratt.tokens.Token; + +/** + * Represents the result of executing a command. + * + * @author bjcul + * + * @param <K> The key type of the tokens + * @param <V> The value type of the tokens + */ +public class CommandResult<K, V> { + /** + * Represents the status of a command execution + * + * @author bjcul + * + */ + public static enum Status { + /** + * The command successfully parsed. + */ + SUCCESS, + /** + * The command failed, in a non-recoverable way + */ + FAIL, + /** + * The command failed. Attempt recovery via backtracking + */ + BACKTRACK + } + + /** + * The status of this command. + */ + public final Status status; + + private Tree<Token<K, V>> success; + + private CommandResult(Status status) { + this.status = status; + } + + /** + * Get the success value of this command, or null if it failed. + * + * @return The success value of the command + */ + public Tree<Token<K, V>> success() { + return success; + } + + /** + * Create a success result + * + * @param <K2> The key type of the token + * @param <V2> The value type of the token + * + * @param succ The tree produced by the command + * + * @return A command result representing a success + */ + public static <K2, V2> CommandResult<K2, V2> success(Tree<Token<K2, V2>> succ) { + CommandResult<K2, V2> result = new CommandResult<>(Status.SUCCESS); + result.success = succ; + return result; + } + + /** + * Create a non-backtracking failure result. + * + * @param <K2> The key type of the token + * @param <V2> The value type of the token + * + * @return A command result representing a non-backtracking fail + */ + public static <K2, V2> CommandResult<K2, V2> fail() { + CommandResult<K2, V2> result = new CommandResult<>(Status.FAIL); + return result; + } + + /** + * Create a backtracking failure result. + * + * @param <K2> The key type of the token + * @param <V2> The value type of the token + * + * @return A command result representing a backtracking fail + */ + public static <K2, V2> CommandResult<K2, V2> backtrack() { + CommandResult<K2, V2> result = new CommandResult<>(Status.BACKTRACK); + return result; + } +} diff --git a/JPratt/src/main/java/bjc/pratt/commands/InitialCommand.java b/JPratt/src/main/java/bjc/pratt/commands/InitialCommand.java index 3a2a8ff..ba544b4 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/InitialCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/InitialCommand.java @@ -31,10 +31,10 @@ public interface InitialCommand<K, V, C> { * @param ctx * The context for the command. * - * @return The tree for this command. + * @return The result of executing the command. * * @throws ParserException * If something goes wrong during parsing. */ - Tree<Token<K, V>> denote(Token<K, V> operator, ParserContext<K, V, C> ctx) throws ParserException; + CommandResult<K, V> denote(Token<K, V> operator, ParserContext<K, V, C> ctx) throws ParserException; } diff --git a/JPratt/src/main/java/bjc/pratt/commands/NonInitialCommand.java b/JPratt/src/main/java/bjc/pratt/commands/NonInitialCommand.java index 12eecb6..02826a9 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/NonInitialCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/NonInitialCommand.java @@ -32,12 +32,12 @@ public abstract class NonInitialCommand<K, V, C> { * @param ctx * The state needed for commands. * - * @return The tree this command forms. + * @return The result of executing the command. * * @throws ParserException * If something went wrong during parsing. */ - public abstract Tree<Token<K, V>> denote(Tree<Token<K, V>> operand, Token<K, V> operator, + public abstract CommandResult<K, V> denote(Tree<Token<K, V>> operand, Token<K, V> operator, ParserContext<K, V, C> ctx) throws ParserException; /** diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/BlockInitialCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/BlockInitialCommand.java index db11484..1d54996 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/BlockInitialCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/BlockInitialCommand.java @@ -3,6 +3,7 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.blocks.ParseBlock; import bjc.pratt.commands.AbstractInitialCommand; +import bjc.pratt.commands.CommandResult; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.utils.parserutils.ParserException; @@ -35,7 +36,7 @@ public class BlockInitialCommand<K, V, C> extends AbstractInitialCommand<K, V, C } @Override - protected Tree<Token<K, V>> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + protected CommandResult<K, V> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { return blck.parse(ctx); } diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/ChainCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/ChainCommand.java index ed7a088..7311eb9 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/ChainCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/ChainCommand.java @@ -4,6 +4,8 @@ import java.util.Set; import bjc.pratt.ParserContext; import bjc.pratt.commands.BinaryPostCommand; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -48,10 +50,12 @@ public class ChainCommand<K, V, C> extends BinaryPostCommand<K, V, C> { } @Override - public Tree<Token<K, V>> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, + public CommandResult<K, V> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - final Tree<Token<K, V>> tree = ctx.parse.parseExpression(1 + leftBinding(), ctx.tokens, ctx.state, + CommandResult<K, V> resOuter = ctx.parse.parseExpression(1 + leftBinding(), ctx.tokens, ctx.state, false); + if (resOuter.status != Status.SUCCESS) return resOuter; + final Tree<Token<K, V>> tree = resOuter.success(); final Tree<Token<K, V>> res = new SimpleTree<>(operator, operand, tree); @@ -59,13 +63,16 @@ public class ChainCommand<K, V, C> extends BinaryPostCommand<K, V, C> { final Token<K, V> tok = ctx.tokens.current(); ctx.tokens.next(); - final Tree<Token<K, V>> other = denote(tree, tok, + CommandResult<K, V> resOther = denote(tree, tok, new ParserContext<>(ctx.tokens, ctx.parse, ctx.state)); + if (resOther.status != Status.SUCCESS) return resOther; + + final Tree<Token<K, V>> other = resOther.success(); - return new SimpleTree<>(chain, res, other); + return CommandResult.success(new SimpleTree<>(chain, res, other)); } - return res; + return CommandResult.success(res); } @Override diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/ConstantCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/ConstantCommand.java index 409adbb..657743c 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/ConstantCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/ConstantCommand.java @@ -1,6 +1,7 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; +import bjc.pratt.commands.CommandResult; import bjc.pratt.commands.InitialCommand; import bjc.pratt.tokens.Token; import bjc.data.Tree; @@ -34,8 +35,8 @@ public class ConstantCommand<K, V, C> implements InitialCommand<K, V, C> { } @Override - public Tree<Token<K, V>> denote(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + public CommandResult<K, V> denote(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - return val; + return CommandResult.success(val); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultInitialCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultInitialCommand.java index 296cb1c..2dfc576 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultInitialCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultInitialCommand.java @@ -1,6 +1,7 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; +import bjc.pratt.commands.CommandResult; import bjc.pratt.commands.InitialCommand; import bjc.pratt.tokens.Token; import bjc.data.Tree; @@ -22,7 +23,7 @@ import bjc.utils.parserutils.ParserException; */ public class DefaultInitialCommand<K, V, C> implements InitialCommand<K, V, C> { @Override - public Tree<Token<K, V>> denote(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + public CommandResult<K, V> denote(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { throw new ParserException("Unexpected token " + operator); } diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultNonInitialCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultNonInitialCommand.java index 797473a..2ae9fb7 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultNonInitialCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/DefaultNonInitialCommand.java @@ -1,6 +1,7 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; +import bjc.pratt.commands.CommandResult; import bjc.pratt.commands.NonInitialCommand; import bjc.pratt.tokens.Token; import bjc.data.Tree; @@ -21,7 +22,7 @@ import bjc.data.Tree; */ public class DefaultNonInitialCommand<K, V, C> extends NonInitialCommand<K, V, C> { @Override - public Tree<Token<K, V>> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, + public CommandResult<K, V> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, final ParserContext<K, V, C> ctx) { throw new UnsupportedOperationException("Default command has no left denotation"); } diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/DenestingCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/DenestingCommand.java index fbcd35c..4935c81 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/DenestingCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/DenestingCommand.java @@ -2,6 +2,8 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.commands.AbstractInitialCommand; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.commands.InitialCommand; import bjc.pratt.tokens.Token; import bjc.data.Tree; @@ -39,8 +41,10 @@ public class DenestingCommand<K, V, C> extends AbstractInitialCommand<K, V, C> { } @Override - protected Tree<Token<K, V>> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + protected CommandResult<K, V> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - return wrapped.denote(operator, ctx).getChild(0); + CommandResult<K, V> res = wrapped.denote(operator, ctx); + if (res.status != Status.SUCCESS) return res; + return CommandResult.success(res.success().getChild(0)); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/GroupingCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/GroupingCommand.java index 1515359..44aa2c1 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/GroupingCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/GroupingCommand.java @@ -3,6 +3,7 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.blocks.ParseBlock; import bjc.pratt.commands.AbstractInitialCommand; +import bjc.pratt.commands.CommandResult; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -43,10 +44,10 @@ public class GroupingCommand<K, V, C> extends AbstractInitialCommand<K, V, C> { } @Override - protected Tree<Token<K, V>> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + protected CommandResult<K, V> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - final Tree<Token<K, V>> opr = innerBlock.parse(ctx); - - return new SimpleTree<>(mark, opr); + final CommandResult<K,V> resOpr = innerBlock.parse(ctx); + Tree<Token<K, V>> opr = resOpr.success(); + return CommandResult.success(new SimpleTree<>(mark, opr)); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/InitialCommands.java b/JPratt/src/main/java/bjc/pratt/commands/impls/InitialCommands.java index 0cfec29..9801788 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/InitialCommands.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/InitialCommands.java @@ -9,6 +9,7 @@ import java.util.function.UnaryOperator; import bjc.pratt.blocks.ParseBlock; import bjc.pratt.commands.InitialCommand; import bjc.pratt.tokens.Token; +import bjc.utils.parserutils.ParserException; import bjc.data.SimpleTree; import bjc.data.Tree; @@ -210,16 +211,6 @@ public class InitialCommands { * @return A command that implements a panfix operator */ public static <K, V, C> InitialCommand<K, V, C> panfix(final int precedence, final K term, final Token<K, V> marker) { - return (operator, ctx) -> { - Tree<Token<K,V>> leftSide = ctx.parse.parseExpression(precedence + 1, ctx.tokens, ctx.state, false); - ctx.tokens.expect(term); - ctx.tokens.next(); - - Tree<Token<K,V>> rightSide = ctx.parse.parseExpression(precedence + 1, ctx.tokens, ctx.state, false); - ctx.tokens.expect(term); - ctx.tokens.next(); - - return new SimpleTree<>(marker, leftSide, rightSide); - }; + return new PanfixCommand<K, V, C>(marker, term, precedence); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/LeafCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/LeafCommand.java index 1223641..c702323 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/LeafCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/LeafCommand.java @@ -1,6 +1,7 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; +import bjc.pratt.commands.CommandResult; import bjc.pratt.commands.InitialCommand; import bjc.pratt.tokens.Token; import bjc.data.Tree; @@ -23,8 +24,8 @@ import bjc.utils.parserutils.ParserException; */ public class LeafCommand<K, V, C> implements InitialCommand<K, V, C> { @Override - public Tree<Token<K, V>> denote(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + public CommandResult<K, V> denote(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - return new SimpleTree<>(operator); + return CommandResult.success(new SimpleTree<>(operator)); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/PanfixCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/PanfixCommand.java new file mode 100644 index 0000000..06e69c1 --- /dev/null +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/PanfixCommand.java @@ -0,0 +1,39 @@ +package bjc.pratt.commands.impls; + +import bjc.data.SimpleTree; +import bjc.data.Tree; +import bjc.pratt.ParserContext; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.InitialCommand; +import bjc.pratt.commands.CommandResult.Status; +import bjc.pratt.tokens.Token; +import bjc.utils.parserutils.ParserException; + +public final class PanfixCommand<K, V, C> implements InitialCommand<K, V, C> { + private final Token<K, V> marker; + private final K term; + private final int precedence; + + public PanfixCommand(Token<K, V> marker, K term, int precedence) { + this.marker = marker; + this.term = term; + this.precedence = precedence; + } + + @Override + public CommandResult<K, V> denote(Token<K, V> operator, ParserContext<K, V, C> ctx) throws ParserException { + CommandResult<K,V> resLeftSide = ctx.parse.parseExpression(precedence + 1, ctx.tokens, ctx.state, false); + if (resLeftSide.status != Status.SUCCESS) return resLeftSide; + Tree<Token<K, V>> leftSide = resLeftSide.success(); + ctx.tokens.expect(term); + ctx.tokens.next(); + + CommandResult<K, V> resRightSide = ctx.parse.parseExpression(precedence + 1, ctx.tokens, ctx.state, false); + if (resLeftSide.status != Status.SUCCESS) return resRightSide; + Tree<Token<K,V>> rightSide = resRightSide.success(); + ctx.tokens.expect(term); + ctx.tokens.next(); + + return CommandResult.success(new SimpleTree<>(marker, leftSide, rightSide)); + } +}
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/PostCircumfixCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/PostCircumfixCommand.java index 78ac1ef..ec2c8fb 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/PostCircumfixCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/PostCircumfixCommand.java @@ -3,6 +3,8 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.blocks.ParseBlock; import bjc.pratt.commands.BinaryPostCommand; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -50,10 +52,11 @@ public class PostCircumfixCommand<K, V, C> extends BinaryPostCommand<K, V, C> { } @Override - public Tree<Token<K, V>> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, + public CommandResult<K, V> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - final Tree<Token<K, V>> inside = innerBlock.parse(ctx); - - return new SimpleTree<>(mark, operand, inside); + final CommandResult<K,V> insideRes = innerBlock.parse(ctx); + if (insideRes.status != Status.SUCCESS) return insideRes; + Tree<Token<K, V>> inside = insideRes.success(); + return CommandResult.success(new SimpleTree<>(mark, operand, inside)); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/PostfixCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/PostfixCommand.java index da587c1..ff370d0 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/PostfixCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/PostfixCommand.java @@ -2,6 +2,7 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.commands.BinaryPostCommand; +import bjc.pratt.commands.CommandResult; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -33,8 +34,8 @@ public class PostfixCommand<K, V, C> extends BinaryPostCommand<K, V, C> { } @Override - public Tree<Token<K, V>> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, + public CommandResult<K, V> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - return new SimpleTree<>(operator, operand); + return CommandResult.success(new SimpleTree<>(operator, operand)); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/PreTernaryCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/PreTernaryCommand.java index e315804..5d5cbe1 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/PreTernaryCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/PreTernaryCommand.java @@ -3,6 +3,8 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.blocks.ParseBlock; import bjc.pratt.commands.AbstractInitialCommand; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -63,14 +65,19 @@ public class PreTernaryCommand<K, V, C> extends AbstractInitialCommand<K, V, C> } @Override - protected Tree<Token<K, V>> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + protected CommandResult<K, V> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - final Tree<Token<K, V>> cond = condBlock.parse(ctx); + final CommandResult<K,V> condRes = condBlock.parse(ctx); + if (condRes.status != Status.SUCCESS) return condRes; + Tree<Token<K, V>> cond = condRes.success(); + + final CommandResult<K,V> op1Res = opblock1.parse(ctx); + if (op1Res.status != Status.SUCCESS) return op1Res; + Tree<Token<K, V>> op1 = op1Res.success(); - final Tree<Token<K, V>> op1 = opblock1.parse(ctx); - - final Tree<Token<K, V>> op2 = opblock2.parse(ctx); - - return new SimpleTree<>(trm, cond, op1, op2); + final CommandResult<K,V> op2Res = opblock2.parse(ctx); + if (op2Res.status != Status.SUCCESS) return op2Res; + Tree<Token<K, V>> op2 = op2Res.success(); + return CommandResult.success(new SimpleTree<>(trm, cond, op1, op2)); } }
\ No newline at end of file diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/TernaryCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/TernaryCommand.java index 174f6fb..786dfec 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/TernaryCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/TernaryCommand.java @@ -3,6 +3,8 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.blocks.ParseBlock; import bjc.pratt.commands.BinaryPostCommand; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -13,14 +15,11 @@ import bjc.utils.parserutils.ParserException; * * @author bjculkin * - * @param <K> - * The key type of the tokens. + * @param <K> The key type of the tokens. * - * @param <V> - * The value type of the tokens. + * @param <V> The value type of the tokens. * - * @param <C> - * The state type of the parser. + * @param <C> The state type of the parser. */ public class TernaryCommand<K, V, C> extends BinaryPostCommand<K, V, C> { private final ParseBlock<K, V, C> innerBlck; @@ -32,25 +31,22 @@ public class TernaryCommand<K, V, C> extends BinaryPostCommand<K, V, C> { /** * Create a new ternary command. * - * @param precedence - * The precedence of this operator. + * @param precedence The precedence of this operator. * - * @param innerBlock - * The representation of the inner block of the expression. + * @param innerBlock The representation of the inner block of the expression. * - * @param marker - * The token to use as the root of the AST node. + * @param marker The token to use as the root of the AST node. * - * @param isNonassoc - * Whether or not the conditional is associative. + * @param isNonassoc Whether or not the conditional is associative. */ public TernaryCommand(final int precedence, final ParseBlock<K, V, C> innerBlock, final Token<K, V> marker, final boolean isNonassoc) { super(precedence); - if(innerBlock == null) + if (innerBlock == null) throw new NullPointerException("Inner block must not be null"); - else if(marker == null) throw new NullPointerException("Marker must not be null"); + else if (marker == null) + throw new NullPointerException("Marker must not be null"); innerBlck = innerBlock; mark = marker; @@ -58,19 +54,22 @@ public class TernaryCommand<K, V, C> extends BinaryPostCommand<K, V, C> { } @Override - public Tree<Token<K, V>> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, + public CommandResult<K, V> denote(final Tree<Token<K, V>> operand, final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - final Tree<Token<K, V>> inner = innerBlck.parse(ctx); - - final Tree<Token<K, V>> outer = ctx.parse.parseExpression(1 + leftBinding(), ctx.tokens, ctx.state, - false); - - return new SimpleTree<>(mark, inner, operand, outer); + final CommandResult<K, V> innerRes = innerBlck.parse(ctx); + if (innerRes.status != Status.SUCCESS) return innerRes; + Tree<Token<K, V>> inner = innerRes.success(); + + final CommandResult<K,V> outerRes = ctx.parse.parseExpression(1 + leftBinding(), ctx.tokens, ctx.state, false); + if (outerRes.status != Status.SUCCESS) return outerRes; + Tree<Token<K, V>> outer = outerRes.success(); + return CommandResult.success(new SimpleTree<>(mark, inner, operand, outer)); } @Override public int nextBinding() { - if(nonassoc) return leftBinding() - 1; + if (nonassoc) + return leftBinding() - 1; return leftBinding(); } diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/TransformingInitialCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/TransformingInitialCommand.java index d39ec90..36f881d 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/TransformingInitialCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/TransformingInitialCommand.java @@ -4,6 +4,8 @@ import java.util.function.UnaryOperator; import bjc.pratt.ParserContext; import bjc.pratt.commands.AbstractInitialCommand; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.commands.InitialCommand; import bjc.pratt.tokens.Token; import bjc.data.Tree; @@ -45,9 +47,12 @@ public class TransformingInitialCommand<K, V, C> extends AbstractInitialCommand< } @Override - protected Tree<Token<K, V>> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + protected CommandResult<K, V> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - return transfrm.apply(internl.denote(operator, ctx)); + CommandResult<K,V> result = internl.denote(operator, ctx); + if (result.status != Status.SUCCESS) return result; + + return CommandResult.success(transfrm.apply(result.success())); } } diff --git a/JPratt/src/main/java/bjc/pratt/commands/impls/UnaryCommand.java b/JPratt/src/main/java/bjc/pratt/commands/impls/UnaryCommand.java index 2e7365b..657c004 100644 --- a/JPratt/src/main/java/bjc/pratt/commands/impls/UnaryCommand.java +++ b/JPratt/src/main/java/bjc/pratt/commands/impls/UnaryCommand.java @@ -2,6 +2,8 @@ package bjc.pratt.commands.impls; import bjc.pratt.ParserContext; import bjc.pratt.commands.AbstractInitialCommand; +import bjc.pratt.commands.CommandResult; +import bjc.pratt.commands.CommandResult.Status; import bjc.pratt.tokens.Token; import bjc.data.Tree; import bjc.data.SimpleTree; @@ -37,10 +39,12 @@ public class UnaryCommand<K, V, C> extends AbstractInitialCommand<K, V, C> { } @Override - protected Tree<Token<K, V>> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) + protected CommandResult<K, V> intNullDenotation(final Token<K, V> operator, final ParserContext<K, V, C> ctx) throws ParserException { - final Tree<Token<K, V>> opr = ctx.parse.parseExpression(nullPwer, ctx.tokens, ctx.state, false); + CommandResult<K,V> result = ctx.parse.parseExpression(nullPwer, ctx.tokens, ctx.state, false); + if (result.status != Status.SUCCESS) return result; + final Tree<Token<K, V>> opr = result.success(); - return new SimpleTree<>(operator, opr); + return CommandResult.success(new SimpleTree<>(operator, opr)); } }
\ No newline at end of file |
