diff options
Diffstat (limited to 'base/src/main/java/bjc/utils/parserutils')
19 files changed, 281 insertions, 259 deletions
diff --git a/base/src/main/java/bjc/utils/parserutils/IPrecedent.java b/base/src/main/java/bjc/utils/parserutils/Precedent.java index eb164b3..33b032c 100644 --- a/base/src/main/java/bjc/utils/parserutils/IPrecedent.java +++ b/base/src/main/java/bjc/utils/parserutils/Precedent.java @@ -7,7 +7,7 @@ package bjc.utils.parserutils; * */ @FunctionalInterface -public interface IPrecedent { +public interface Precedent { /** * Create a new object with set precedence * @@ -15,7 +15,7 @@ public interface IPrecedent { * The precedence of the object to handle * @return A new object with set precedence */ - public static IPrecedent newSimplePrecedent(final int precedence) { + public static Precedent newSimplePrecedent(final int precedence) { return () -> precedence; } diff --git a/base/src/main/java/bjc/utils/parserutils/ShuntingYard.java b/base/src/main/java/bjc/utils/parserutils/ShuntingYard.java index 2418517..f0475ff 100644 --- a/base/src/main/java/bjc/utils/parserutils/ShuntingYard.java +++ b/base/src/main/java/bjc/utils/parserutils/ShuntingYard.java @@ -6,8 +6,8 @@ import java.util.function.Function; import bjc.funcdata.FunctionalList; import bjc.funcdata.FunctionalMap; -import bjc.funcdata.IList; -import bjc.funcdata.IMap; +import bjc.funcdata.ListEx; +import bjc.funcdata.MapEx; import bjc.utils.funcutils.StringUtils; /** @@ -25,7 +25,7 @@ public class ShuntingYard<TokenType> { * @author ben * */ - public static enum Operator implements IPrecedent { + public static enum Operator implements Precedent { /** * Represents addition. */ @@ -59,7 +59,7 @@ public class ShuntingYard<TokenType> { /* * Holds all the shuntable operations. */ - private IMap<String, IPrecedent> operators; + private MapEx<String, Precedent> operators; /** * Create a new shunting yard with a default set of operators. @@ -95,7 +95,7 @@ public class ShuntingYard<TokenType> { /* * Create the precedence marker */ - final IPrecedent prec = IPrecedent.newSimplePrecedent(precedence); + final Precedent prec = Precedent.newSimplePrecedent(precedence); this.addOp(operator, prec); } @@ -109,14 +109,12 @@ public class ShuntingYard<TokenType> { * @param precedence * The precedence of the operator. */ - public void addOp(final String operator, final IPrecedent precedence) { + public void addOp(final String operator, final Precedent precedence) { /* * Complain about trying to add an incorrect operator */ - if (operator == null) - throw new NullPointerException("Operator must not be null"); - else if (precedence == null) - throw new NullPointerException("Precedence must not be null"); + if (operator == null) throw new NullPointerException("Operator must not be null"); + else if (precedence == null) throw new NullPointerException("Precedence must not be null"); /* * Add the operator to the ones we handle @@ -140,8 +138,8 @@ public class ShuntingYard<TokenType> { /* * Get the precedence of operators */ - final int rightPrecedence = operators.get(right).getPrecedence(); - final int leftPrecedence = operators.get(left).getPrecedence(); + final int rightPrecedence = operators.get(right).get().getPrecedence(); + final int leftPrecedence = operators.get(left).get().getPrecedence(); /* * Evaluate what we were asked @@ -160,20 +158,18 @@ public class ShuntingYard<TokenType> { * * @return A list of tokens in postfix notation. */ - public IList<TokenType> postfix(final IList<String> input, + public ListEx<TokenType> postfix(final ListEx<String> input, final Function<String, TokenType> transformer) { /* * Check our input */ - if (input == null) - throw new NullPointerException("Input must not be null"); - else if (transformer == null) - throw new NullPointerException("Transformer must not be null"); + if (input == null) throw new NullPointerException("Input must not be null"); + else if (transformer == null) throw new NullPointerException("Transformer must not be null"); /* * Here's what we're handing back */ - final IList<TokenType> output = new FunctionalList<>(); + final ListEx<TokenType> output = new FunctionalList<>(); /* * The stack to put operators on @@ -226,9 +222,7 @@ public class ShuntingYard<TokenType> { } } - for (String token : stack) { - output.add(transformer.apply(token)); - } + for (String token : stack) output.add(transformer.apply(token)); return output; } @@ -244,10 +238,7 @@ public class ShuntingYard<TokenType> { /* * Check if we want to remove all operators */ - if (operator == null) { - operators = new FunctionalMap<>(); - } else { - operators.remove(operator); - } + if (operator == null) operators = new FunctionalMap<>(); + else operators.remove(operator); } } diff --git a/base/src/main/java/bjc/utils/parserutils/StringDescaper.java b/base/src/main/java/bjc/utils/parserutils/StringDescaper.java index f8868e6..7052588 100644 --- a/base/src/main/java/bjc/utils/parserutils/StringDescaper.java +++ b/base/src/main/java/bjc/utils/parserutils/StringDescaper.java @@ -12,7 +12,7 @@ import java.util.regex.Pattern; import java.util.regex.PatternSyntaxException; /** - * <<<<<<< Updated upstream Customizable string escapes. + * Customizable string escapes. * * @author Benjamin Culkin */ diff --git a/base/src/main/java/bjc/utils/parserutils/TokenTransformer.java b/base/src/main/java/bjc/utils/parserutils/TokenTransformer.java deleted file mode 100644 index 6cf2da5..0000000 --- a/base/src/main/java/bjc/utils/parserutils/TokenTransformer.java +++ /dev/null @@ -1,148 +0,0 @@ -package bjc.utils.parserutils; - -import java.util.Deque; -import java.util.function.Consumer; -import java.util.function.Function; -import java.util.function.Predicate; -import java.util.function.UnaryOperator; - -import bjc.data.IHolder; -import bjc.data.ITree; -import bjc.data.Pair; -import bjc.data.Tree; -import bjc.utils.parserutils.TreeConstructor.ConstructorState; -import bjc.utils.parserutils.TreeConstructor.QueueFlattener; - -/* - * Handle creating ASTs from tokens. - */ -final class TokenTransformer<TokenType> implements Consumer<TokenType> { - /* - * Handle operators - */ - private final class OperatorHandler - implements UnaryOperator<ConstructorState<TokenType>> { - /* The handled element. */ - private final TokenType element; - - /* Create a new operator handler. */ - public OperatorHandler(final TokenType element) { - this.element = element; - } - - @Override - public ConstructorState<TokenType> apply(final ConstructorState<TokenType> pair) { - /* - * Replace the current AST with the result of handling an operator - */ - return new ConstructorState<>( - pair.bindLeft(queuedASTs -> handleOperator(queuedASTs))); - } - - private ConstructorState<TokenType> - handleOperator(final Deque<ITree<TokenType>> queuedASTs) { - /* - * The AST we're going to hand back - */ - ITree<TokenType> newAST; - - /* - * Handle special operators - */ - if (isSpecialOperator.test(element)) { - newAST = handleSpecialOperator.apply(element).apply(queuedASTs); - } else { - /* - * Error if we don't have enough for a binary operator - */ - if (queuedASTs.size() < 2) { - final String msg = String.format( - "Attempted to parse binary operator without enough operands\n\tProblem operator is: %s\n\tPossible operand is: %s", - element.toString(), queuedASTs.peek().toString()); - - throw new IllegalStateException(msg); - } - - /* - * Grab the two operands - */ - final ITree<TokenType> right = queuedASTs.pop(); - final ITree<TokenType> left = queuedASTs.pop(); - - /* - * Create a new AST - */ - newAST = new Tree<>(element, left, right); - } - - /* - * Stick it onto the stack - */ - queuedASTs.push(newAST); - - /* - * Hand back the state - */ - return new ConstructorState<>(queuedASTs, newAST); - } - } - - /* The initial state of the transformer. */ - private final IHolder<ConstructorState<TokenType>> initialState; - - /* The predicate tot use to detect operators. */ - private final Predicate<TokenType> operatorPredicate; - - /* The predicate for detecting special operators. */ - private final Predicate<TokenType> isSpecialOperator; - /* The function for handling special operators. */ - private final Function<TokenType, QueueFlattener<TokenType>> handleSpecialOperator; - - /** - * Create a new transformer - * - * @param initialState - * The initial state of the transformer. - * - * @param operatorPredicate - * The predicate to use to identify operators. - * - * @param isSpecialOperator - * The predicate used to identify special - * operators. - * - * @param handleSpecialOperator - * The function used for handling special - * operators. - */ - public TokenTransformer(final IHolder<ConstructorState<TokenType>> initialState, - final Predicate<TokenType> operatorPredicate, - final Predicate<TokenType> isSpecialOperator, - final Function<TokenType, QueueFlattener<TokenType>> handleSpecialOperator) { - this.initialState = initialState; - this.operatorPredicate = operatorPredicate; - this.isSpecialOperator = isSpecialOperator; - this.handleSpecialOperator = handleSpecialOperator; - } - - @Override - public void accept(final TokenType element) { - /* - * Handle operators - */ - if (operatorPredicate.test(element)) { - initialState.transform(new OperatorHandler(element)); - } else { - final ITree<TokenType> newAST = new Tree<>(element); - - /* - * Insert the new tree into the AST - */ - initialState.transform(pair -> new ConstructorState<>(pair.bindLeft(queue -> { - queue.push(newAST); - - return new Pair<>(queue, newAST); - }))); - } - } -} diff --git a/base/src/main/java/bjc/utils/parserutils/TokenUtils.java b/base/src/main/java/bjc/utils/parserutils/TokenUtils.java index 81a7ba0..860bbdf 100644 --- a/base/src/main/java/bjc/utils/parserutils/TokenUtils.java +++ b/base/src/main/java/bjc/utils/parserutils/TokenUtils.java @@ -4,13 +4,13 @@ import static bjc.utils.misc.PropertyDB.applyFormat; import static bjc.utils.misc.PropertyDB.getCompiledRegex; import static bjc.utils.misc.PropertyDB.getRegex; -import java.util.LinkedList; -import java.util.List; +import java.util.*; import java.util.regex.Matcher; import java.util.regex.Pattern; +import bjc.data.*; import bjc.funcdata.FunctionalList; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; import bjc.utils.parserutils.splitter.TokenSplitter; /** @@ -28,7 +28,7 @@ public class TokenUtils { */ public static class StringTokenSplitter implements TokenSplitter { @Override - public IList<String> split(final String input) { + public ListEx<String> split(final String input) { return new FunctionalList<>(TokenUtils.removeDQuotedStrings(input)); } } @@ -316,4 +316,28 @@ public class TokenUtils { return false; } } + + /** + * Split a line into a series of space-separated arguments, including string + * literals. + * + * @param com + * The command to split from + * @return The split arguments. + */ + public static List<String> processArguments(String com) { + List<String> strings = new ArrayList<>(); + + BooleanToggle togg = new BooleanToggle(); + + for (String strang : removeDQuotedStrings(com)) { + if (togg.get()) { + strings.add(descapeString(strang)); + } else { + for (String strung : strang.split("\\s+")) strings.add(strung); + } + } + + return strings; + } } diff --git a/base/src/main/java/bjc/utils/parserutils/TreeConstructor.java b/base/src/main/java/bjc/utils/parserutils/TreeConstructor.java index 3c7509b..bd907b5 100644 --- a/base/src/main/java/bjc/utils/parserutils/TreeConstructor.java +++ b/base/src/main/java/bjc/utils/parserutils/TreeConstructor.java @@ -2,15 +2,11 @@ package bjc.utils.parserutils; import java.util.Deque; import java.util.LinkedList; -import java.util.function.Function; -import java.util.function.Predicate; +import java.util.function.*; -import bjc.data.IHolder; -import bjc.data.IPair; -import bjc.data.ITree; -import bjc.data.Identity; -import bjc.data.Pair; -import bjc.funcdata.IList; +import bjc.data.*; +import bjc.funcdata.ListEx; +import bjc.utils.parserutils.TreeConstructor.*; /** * Creates a parse tree from a postfix expression. @@ -26,7 +22,7 @@ public class TreeConstructor { * The token type of the tree. */ public interface QueueFlattener<TokenType> - extends Function<Deque<ITree<TokenType>>, ITree<TokenType>> { + extends Function<Deque<Tree<TokenType>>, Tree<TokenType>> { /* * Alias */ @@ -34,14 +30,14 @@ public class TreeConstructor { /* Alias for constructor state. */ static final class ConstructorState<TokenType> - extends Pair<Deque<ITree<TokenType>>, ITree<TokenType>> { - public ConstructorState(final Deque<ITree<TokenType>> left, - final ITree<TokenType> right) { + extends SimplePair<Deque<Tree<TokenType>>, Tree<TokenType>> { + public ConstructorState(final Deque<Tree<TokenType>> left, + final Tree<TokenType> right) { super(left, right); } public ConstructorState( - final IPair<Deque<ITree<TokenType>>, ITree<TokenType>> par) { + final Pair<Deque<Tree<TokenType>>, Tree<TokenType>> par) { super(par.getLeft(), par.getRight()); } } @@ -63,8 +59,8 @@ public class TreeConstructor { * * @return A AST from the expression. */ - public static <TokenType> ITree<TokenType> constructTree( - final IList<TokenType> tokens, final Predicate<TokenType> isOperator) { + public static <TokenType> Tree<TokenType> constructTree( + final ListEx<TokenType> tokens, final Predicate<TokenType> isOperator) { /* Construct a tree with no special operators */ return constructTree(tokens, isOperator, op -> false, null); } @@ -96,26 +92,27 @@ public class TreeConstructor { * @return A AST from the expression. * */ - public static <TokenType> ITree<TokenType> constructTree( - final IList<TokenType> tokens, final Predicate<TokenType> isOperator, + public static <TokenType> Tree<TokenType> constructTree( + final ListEx<TokenType> tokens, final Predicate<TokenType> isOperator, final Predicate<TokenType> isSpecialOperator, final Function<TokenType, QueueFlattener<TokenType>> handleSpecialOperator) { /* * Make sure our parameters are valid */ - if (tokens == null) + if (tokens == null) { throw new NullPointerException("Tokens must not be null"); - else if (isOperator == null) + } else if (isOperator == null) { throw new NullPointerException("Operator predicate must not be null"); - else if (isSpecialOperator == null) + } else if (isSpecialOperator == null) { throw new NullPointerException( "Special operator determiner must not be null"); + } final ConstructorState<TokenType> cstate = new ConstructorState<>(new LinkedList<>(), null); /* Here is the state for the tree construction */ - final IHolder<ConstructorState<TokenType>> initialState = new Identity<>(cstate); + final Holder<ConstructorState<TokenType>> initialState = new Identity<>(cstate); /* Transform each of the tokens */ final TokenTransformer<TokenType> trans = new TokenTransformer<>(initialState, @@ -127,3 +124,140 @@ public class TreeConstructor { return initialState.unwrap(ConstructorState::getRight); } } + +/* + * Transform function on tokens + */ +class TokenTransformer<TokenType> implements Consumer<TokenType> { + /* + * Handle operators + */ + private final class OperatorHandler + implements UnaryOperator<ConstructorState<TokenType>> { + /* The handled element. */ + private final TokenType element; + + /* Create a new operator handler. */ + public OperatorHandler(final TokenType element) { + this.element = element; + } + + @Override + public ConstructorState<TokenType> apply(final ConstructorState<TokenType> pair) { + /* + * Replace the current AST with the result of handling an operator + */ + return new ConstructorState<>( + pair.bindLeft(queuedASTs -> handleOperator(queuedASTs))); + } + + private ConstructorState<TokenType> + handleOperator(final Deque<Tree<TokenType>> queuedASTs) { + /* + * The AST we're going to hand back + */ + Tree<TokenType> newAST; + + /* + * Handle special operators + */ + if (isSpecialOperator.test(element)) { + newAST = handleSpecialOperator.apply(element).apply(queuedASTs); + } else { + /* + * Error if we don't have enough for a binary operator + */ + if (queuedASTs.size() < 2) { + final String msg = String.format( + "Attempted to parse binary operator without enough operands\n\tProblem operator is: %s\n\tPossible operand is: %s", + element.toString(), queuedASTs.peek().toString()); + + throw new IllegalStateException(msg); + } + + /* + * Grab the two operands + */ + final Tree<TokenType> right = queuedASTs.pop(); + final Tree<TokenType> left = queuedASTs.pop(); + + /* + * Create a new AST + */ + newAST = new SimpleTree<>(element, left, right); + } + + /* + * Stick it onto the stack + */ + queuedASTs.push(newAST); + + /* + * Hand back the state + */ + return new ConstructorState<>(queuedASTs, newAST); + } + } + + /* The initial state of the transformer. */ + private final Holder<ConstructorState<TokenType>> initialState; + + /* The predicate tot use to detect operators. */ + private final Predicate<TokenType> operatorPredicate; + + /* The predicate for detecting special operators. */ + private final Predicate<TokenType> isSpecialOperator; + /* The function for handling special operators. */ + private final Function<TokenType, QueueFlattener<TokenType>> handleSpecialOperator; + + /** + * Create a new transformer + * + * @param initialState + * The initial state of the transformer. + * + * @param operatorPredicate + * The predicate to use to identify operators. + * + * @param isSpecialOperator + * The predicate used to identify special + * operators. + * + * @param handleSpecialOperator + * The function used for handling special + * operators. + */ + public TokenTransformer(final Holder<ConstructorState<TokenType>> initialState, + final Predicate<TokenType> operatorPredicate, + final Predicate<TokenType> isSpecialOperator, + final Function<TokenType, QueueFlattener<TokenType>> handleSpecialOperator) { + this.initialState = initialState; + this.operatorPredicate = operatorPredicate; + this.isSpecialOperator = isSpecialOperator; + this.handleSpecialOperator = handleSpecialOperator; + } + + @Override + public void accept(final TokenType element) { + /* + * Handle operators + */ + if (operatorPredicate.test(element)) { + initialState.transform(new OperatorHandler(element)); + } else { + final Tree<TokenType> newAST = new SimpleTree<>(element); + + /* + * Insert the new tree into the AST + */ + initialState.transform(pair -> new ConstructorState<>( + pair.bindLeft(queue -> { + queue.push(newAST); + + return new SimplePair<>(queue, newAST); + }) + ) + ); + } + } +}
\ No newline at end of file diff --git a/base/src/main/java/bjc/utils/parserutils/delims/DelimiterGroup.java b/base/src/main/java/bjc/utils/parserutils/delims/DelimiterGroup.java index ba61531..75f777c 100644 --- a/base/src/main/java/bjc/utils/parserutils/delims/DelimiterGroup.java +++ b/base/src/main/java/bjc/utils/parserutils/delims/DelimiterGroup.java @@ -11,12 +11,12 @@ import java.util.Set; import java.util.function.BiPredicate; import java.util.function.Function; -import bjc.data.IPair; -import bjc.data.ITree; import bjc.data.Pair; import bjc.data.Tree; +import bjc.data.SimplePair; +import bjc.data.SimpleTree; import bjc.funcdata.FunctionalList; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; /** * Represents a possible delimiter group to match. @@ -37,12 +37,12 @@ public class DelimiterGroup<T> { /* * The contents of this group. */ - private final Deque<ITree<T>> contents; + private final Deque<Tree<T>> contents; /* * The contents of the current subgroup. */ - private IList<ITree<T>> currentGroup; + private ListEx<Tree<T>> currentGroup; /* * The token that opened the group, and any opening parameters. @@ -74,7 +74,7 @@ public class DelimiterGroup<T> { * @param itm * The item to add to this group instance. */ - public void addItem(final ITree<T> itm) { + public void addItem(final Tree<T> itm) { currentGroup.add(itm); } @@ -91,8 +91,8 @@ public class DelimiterGroup<T> { /* * Add all of the contents to the subgroup. */ - final ITree<T> subgroupContents = new Tree<>(chars.contents); - for (final ITree<T> itm : currentGroup) { + final Tree<T> subgroupContents = new SimpleTree<>(chars.contents); + for (final Tree<T> itm : currentGroup) { subgroupContents.addChild(itm); } @@ -100,7 +100,7 @@ public class DelimiterGroup<T> { * Handle subordinate sub-groups. */ while (!contents.isEmpty()) { - final ITree<T> possibleSubordinate = contents.peek(); + final Tree<T> possibleSubordinate = contents.peek(); /* * Subordinate lower priority subgroups. @@ -118,8 +118,8 @@ public class DelimiterGroup<T> { } } - final Tree<T> subgroup - = new Tree<>(chars.subgroup, subgroupContents, new Tree<>(marker)); + final SimpleTree<T> subgroup + = new SimpleTree<>(chars.subgroup, subgroupContents, new SimpleTree<>(marker)); contents.push(subgroup); @@ -137,7 +137,7 @@ public class DelimiterGroup<T> { * * @return This group as a tree. */ - public ITree<T> toTree(final T closer, final SequenceCharacteristics<T> chars) { + public Tree<T> toTree(final T closer, final SequenceCharacteristics<T> chars) { /* * Mark any implied subgroups. */ @@ -146,7 +146,7 @@ public class DelimiterGroup<T> { } /* The resulting tree. */ - final ITree<T> res = new Tree<>(chars.contents); + final Tree<T> res = new SimpleTree<>(chars.contents); /* * Add either the contents of the current group, or subgroups if they're @@ -162,7 +162,7 @@ public class DelimiterGroup<T> { currentGroup.forEach(res::addChild); } - return new Tree<>(groupName, new Tree<>(opener), res, new Tree<>(closer)); + return new SimpleTree<>(groupName, new SimpleTree<>(opener), res, new SimpleTree<>(closer)); } @Override @@ -259,18 +259,18 @@ public class DelimiterGroup<T> { * * @return The name of the group T opens, or null if it doesn't open one. */ - public IPair<T, T[]> doesOpen(final T marker) { + public Pair<T, T[]> doesOpen(final T marker) { if (openDelimiters.containsKey(marker)) - return new Pair<>(openDelimiters.get(marker), null); + return new SimplePair<>(openDelimiters.get(marker), null); - for (final Function<T, IPair<T, T[]>> pred : predOpeners) { - final IPair<T, T[]> par = pred.apply(marker); + for (final Function<T, Pair<T, T[]>> pred : predOpeners) { + final Pair<T, T[]> par = pred.apply(marker); if (par.getLeft() != null) return par; } - return new Pair<>(null, null); + return new SimplePair<>(null, null); } /** @@ -312,7 +312,7 @@ public class DelimiterGroup<T> { private final Map<T, T> impliedSubgroups; /* Allows more complex openings */ - private final List<Function<T, IPair<T, T[]>>> predOpeners; + private final List<Function<T, Pair<T, T[]>>> predOpeners; /* Allow more complex closings */ private final List<BiPredicate<T, T[]>> predClosers; @@ -562,7 +562,7 @@ public class DelimiterGroup<T> { * @param pred * The predicate that defines the opener and its parameters. */ - public void addPredOpener(final Function<T, IPair<T, T[]>> pred) { + public void addPredOpener(final Function<T, Pair<T, T[]>> pred) { predOpeners.add(pred); } diff --git a/base/src/main/java/bjc/utils/parserutils/delims/RegexOpener.java b/base/src/main/java/bjc/utils/parserutils/delims/RegexOpener.java index f08201c..db5c3ca 100644 --- a/base/src/main/java/bjc/utils/parserutils/delims/RegexOpener.java +++ b/base/src/main/java/bjc/utils/parserutils/delims/RegexOpener.java @@ -4,8 +4,8 @@ import java.util.function.Function; import java.util.regex.Matcher; import java.util.regex.Pattern; -import bjc.data.IPair; import bjc.data.Pair; +import bjc.data.SimplePair; /** * A predicated opener for use with {@link RegexCloser} @@ -13,7 +13,7 @@ import bjc.data.Pair; * @author bjculkin * */ -public class RegexOpener implements Function<String, IPair<String, String[]>> { +public class RegexOpener implements Function<String, Pair<String, String[]>> { /* The name of the group. */ private final String name; /* The pattern that marks an opening group. */ @@ -35,7 +35,7 @@ public class RegexOpener implements Function<String, IPair<String, String[]>> { } @Override - public IPair<String, String[]> apply(final String str) { + public Pair<String, String[]> apply(final String str) { final Matcher m = patt.matcher(str); if (m.matches()) { @@ -47,9 +47,9 @@ public class RegexOpener implements Function<String, IPair<String, String[]>> { parms[i] = m.group(i); } - return new Pair<>(name, parms); + return new SimplePair<>(name, parms); } - return new Pair<>(null, null); + return new SimplePair<>(null, null); } } diff --git a/base/src/main/java/bjc/utils/parserutils/delims/SequenceDelimiter.java b/base/src/main/java/bjc/utils/parserutils/delims/SequenceDelimiter.java index 195c1f1..b3f6dc4 100644 --- a/base/src/main/java/bjc/utils/parserutils/delims/SequenceDelimiter.java +++ b/base/src/main/java/bjc/utils/parserutils/delims/SequenceDelimiter.java @@ -9,13 +9,13 @@ import com.google.common.collect.HashMultiset; import com.google.common.collect.Multimap; import com.google.common.collect.Multiset; -import bjc.data.IPair; -import bjc.data.ITree; +import bjc.data.Pair; import bjc.data.Tree; +import bjc.data.SimpleTree; import bjc.esodata.PushdownMap; import bjc.esodata.SimpleStack; import bjc.esodata.Stack; -import bjc.funcdata.IMap; +import bjc.funcdata.MapEx; import bjc.utils.funcutils.StringUtils; /** @@ -82,7 +82,7 @@ public class SequenceDelimiter<T> { * delimitation. * */ - public ITree<T> delimitSequence(final SequenceCharacteristics<T> chars, + public Tree<T> delimitSequence(final SequenceCharacteristics<T> chars, @SuppressWarnings("unchecked") final T... seq) throws DelimiterException { if (initialGroup == null) { throw new NullPointerException("Initial group must be specified."); @@ -105,7 +105,7 @@ public class SequenceDelimiter<T> { allowedDelimiters.push(HashMultimap.create()); /* Map of who forbid what for debugging purposes. */ - final IMap<T, T> whoForbid = new PushdownMap<>(); + final MapEx<T, T> whoForbid = new PushdownMap<>(); /* * Process each member of the sequence. @@ -114,7 +114,7 @@ public class SequenceDelimiter<T> { final T tok = seq[i]; /* Check if this token could open a group. */ - final IPair<T, T[]> possibleOpenPar = groupStack.top().doesOpen(tok); + final Pair<T, T[]> possibleOpenPar = groupStack.top().doesOpen(tok); T possibleOpen = possibleOpenPar.getLeft(); if (possibleOpen == null) { @@ -143,11 +143,7 @@ public class SequenceDelimiter<T> { if (isForbidden(groupStack, forbiddenDelimiters, possibleOpen)) { T forbiddenBy; - if (whoForbid.containsKey(tok)) { - forbiddenBy = whoForbid.get(tok); - } else { - forbiddenBy = groupStack.top().getName(); - } + forbiddenBy = whoForbid.get(tok).orElse(groupStack.top().getName()); final String ctxList = StringUtils.toEnglishList(groupStack.toArray(), "then"); @@ -221,7 +217,7 @@ public class SequenceDelimiter<T> { groupStack.top().markSubgroup(tok, chars); } else { /* Add an item to the group. */ - groupStack.top().addItem(new Tree<>(tok)); + groupStack.top().addItem(new SimpleTree<>(tok)); } } diff --git a/base/src/main/java/bjc/utils/parserutils/delims/StringDelimiter.java b/base/src/main/java/bjc/utils/parserutils/delims/StringDelimiter.java index 6035ede..575066d 100644 --- a/base/src/main/java/bjc/utils/parserutils/delims/StringDelimiter.java +++ b/base/src/main/java/bjc/utils/parserutils/delims/StringDelimiter.java @@ -1,6 +1,6 @@ package bjc.utils.parserutils.delims; -import bjc.data.ITree; +import bjc.data.Tree; /** * A sequence delimiter specialized for strings. @@ -26,7 +26,7 @@ public class StringDelimiter extends SequenceDelimiter<String> { * * @see SequenceDelimiter */ - public ITree<String> delimitSequence(final String... seq) throws DelimiterException { + public Tree<String> delimitSequence(final String... seq) throws DelimiterException { return super.delimitSequence( new SequenceCharacteristics<>("root", "contents", "subgroup"), seq); } diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/ChainTokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/ChainTokenSplitter.java index 0844b5b..c60b6f2 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/ChainTokenSplitter.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/ChainTokenSplitter.java @@ -1,7 +1,7 @@ package bjc.utils.parserutils.splitter; import bjc.funcdata.FunctionalList; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; /** * A token splitter that chains several other splitters together. @@ -10,7 +10,7 @@ import bjc.funcdata.IList; * */ public class ChainTokenSplitter implements TokenSplitter { - private final IList<TokenSplitter> spliters; + private final ListEx<TokenSplitter> spliters; /** * Create a new chain token splitter. @@ -40,8 +40,8 @@ public class ChainTokenSplitter implements TokenSplitter { } @Override - public IList<String> split(final String input) { - final IList<String> initList = new FunctionalList<>(input); + public ListEx<String> split(final String input) { + final ListEx<String> initList = new FunctionalList<>(input); return spliters.reduceAux(initList, (splitter, strangs) -> strangs.flatMap(splitter::split)); } diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/ConfigurableTokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/ConfigurableTokenSplitter.java index 16c1dc3..26d9dbe 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/ConfigurableTokenSplitter.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/ConfigurableTokenSplitter.java @@ -6,7 +6,7 @@ import java.util.LinkedHashSet; import java.util.Set; import java.util.regex.Pattern; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; /** * Split a string into pieces around a regular expression, and offer an easy way @@ -111,7 +111,7 @@ public class ConfigurableTokenSplitter extends SimpleTokenSplitter { } @Override - public IList<String> split(final String input) { + public ListEx<String> split(final String input) { if (spliter == null) throw new IllegalStateException("Must compile splitter before use"); diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/ExcludingTokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/ExcludingTokenSplitter.java index 9a0cd65..52ce4bf 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/ExcludingTokenSplitter.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/ExcludingTokenSplitter.java @@ -5,7 +5,7 @@ import java.util.Set; import java.util.function.Predicate; import bjc.funcdata.FunctionalList; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; /** * A token splitter that will not split certain tokens. @@ -15,7 +15,7 @@ import bjc.funcdata.IList; */ public class ExcludingTokenSplitter implements TokenSplitter { private final Set<String> literalExclusions; - private final IList<Predicate<String>> predExclusions; + private final ListEx<Predicate<String>> predExclusions; private final TokenSplitter spliter; @@ -59,7 +59,7 @@ public class ExcludingTokenSplitter implements TokenSplitter { } @Override - public IList<String> split(final String input) { + public ListEx<String> split(final String input) { if (literalExclusions.contains(input)) return new FunctionalList<>(input); else if (predExclusions.anyMatch(pred -> pred.test(input))) diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/FilteredTokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/FilteredTokenSplitter.java index 85d72e2..70abbbc 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/FilteredTokenSplitter.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/FilteredTokenSplitter.java @@ -2,7 +2,7 @@ package bjc.utils.parserutils.splitter; import java.util.function.Predicate; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; /** * A token splitter that removes tokens that match a predicate from the stream @@ -31,7 +31,7 @@ public class FilteredTokenSplitter implements TokenSplitter { } @Override - public IList<String> split(String input) { + public ListEx<String> split(String input) { return source.split(input).getMatching(filter); } } diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/IdentityTokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/IdentityTokenSplitter.java new file mode 100644 index 0000000..b3b1b29 --- /dev/null +++ b/base/src/main/java/bjc/utils/parserutils/splitter/IdentityTokenSplitter.java @@ -0,0 +1,16 @@ +package bjc.utils.parserutils.splitter; + +import bjc.funcdata.*; + +/** + * The token splitter that doesn't actually perform any splitting. + * + * @author Ben Culkin + * + */ +public class IdentityTokenSplitter implements TokenSplitter { + @Override + public ListEx<String> split(String input) { + return new FunctionalList<>(input); + } +} diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/SimpleTokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/SimpleTokenSplitter.java index 6d88b20..df9ce70 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/SimpleTokenSplitter.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/SimpleTokenSplitter.java @@ -2,7 +2,7 @@ package bjc.utils.parserutils.splitter; import java.util.regex.Pattern; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; import bjc.functypes.ID; import bjc.utils.ioutils.RegexStringEditor; @@ -39,7 +39,7 @@ public class SimpleTokenSplitter implements TokenSplitter { } @Override - public IList<String> split(final String input) { + public ListEx<String> split(final String input) { if (keepDelim) { return RegexStringEditor.mapOccurances(input, spliter, ID.id(), ID.id()); } diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitter.java index 59e73e8..e833c21 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitter.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitter.java @@ -1,6 +1,6 @@ package bjc.utils.parserutils.splitter; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; /** * Split a string into a list of pieces. @@ -17,5 +17,5 @@ public interface TokenSplitter { * * @return The pieces of the string. */ - public IList<String> split(String input); + public ListEx<String> split(String input); } diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitters.java b/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitters.java index 15d6b8b..4aed8f6 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitters.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/TokenSplitters.java @@ -25,6 +25,15 @@ public class TokenSplitters { } /** + * Create a new identity token splitter, which doesn't actually do any splitting. + * + * @return A new identity splitter. + */ + public static TokenSplitter identitySplitter() { + return new IdentityTokenSplitter(); + } + + /** * Create a new transforming token splitter. * * @param splitter diff --git a/base/src/main/java/bjc/utils/parserutils/splitter/TransformTokenSplitter.java b/base/src/main/java/bjc/utils/parserutils/splitter/TransformTokenSplitter.java index b9fbedc..63c3206 100644 --- a/base/src/main/java/bjc/utils/parserutils/splitter/TransformTokenSplitter.java +++ b/base/src/main/java/bjc/utils/parserutils/splitter/TransformTokenSplitter.java @@ -2,7 +2,7 @@ package bjc.utils.parserutils.splitter; import java.util.function.UnaryOperator; -import bjc.funcdata.IList; +import bjc.funcdata.ListEx; /** * A token splitter that performs a transform on the tokens from another @@ -31,7 +31,7 @@ public class TransformTokenSplitter implements TokenSplitter { } @Override - public IList<String> split(String input) { + public ListEx<String> split(String input) { return source.split(input).map(transform); } |
