TerminalParser { public static Parser<Token> adjacent(Parser<List<Token>> parser, final Parser<?> otherwise) { return parser.next(tokens -> { if (tokens.isEmpty()) return Parsers.always(); int offset = tokens.get(0).index(); for (Token token : tokens) { if (token.index() != offset) { return otherwise; } offset += token.length(); } return Parsers.always(); }).atomic().source().token(); }  static Parser<Token> adjacent(Parser<List<Token>> parser, final Parser<?> otherwise); static Parser<Token> adjacent(String operator); static Parser<?> term(String name); static Parser<?> phrase(String phrase);  }
@Test public void testAdjacent() { assertOperator(TerminalParser.adjacent(""), ""); assertOperator(TerminalParser.adjacent("<"), "<"); assertOperator(TerminalParser.adjacent(">>"), ">>"); assertOperator(TerminalParser.adjacent(">>>"), ">>>"); assertOperator(TerminalParser.adjacent("<<"), "<<"); assertOperator(TerminalParser.adjacent("<+>"), "<+>"); assertFailure(TerminalParser.adjacent(">>"), "> >", 1, 4); assertFailure(TerminalParser.adjacent(">>"), ">+", 1, 2); assertParser(TerminalParser.adjacent(">>").optional(), ">+", null, ">+"); assertOperator(TerminalParser.adjacent(">>").or(TerminalParser.adjacent(">+")), ">+"); }