package aima.core.logic.fol.parsing; import java.util.HashSet; import java.util.Set; import aima.core.logic.common.Lexer; import aima.core.logic.common.LexerException; import aima.core.logic.common.LogicTokenTypes; import aima.core.logic.common.Token; import aima.core.logic.fol.Connectors; import aima.core.logic.fol.Quantifiers; import aima.core.logic.fol.domain.FOLDomain; /** * @author Ciaran O'Reilly * @author Ravi Mohan * */ public class FOLLexer extends Lexer { private FOLDomain domain; private Set<String> connectors, quantifiers; public FOLLexer(FOLDomain domain) { this.domain = domain; connectors = new HashSet<String>(); connectors.add(Connectors.NOT); connectors.add(Connectors.AND); connectors.add(Connectors.OR); connectors.add(Connectors.IMPLIES); connectors.add(Connectors.BICOND); quantifiers = new HashSet<String>(); quantifiers.add(Quantifiers.FORALL); quantifiers.add(Quantifiers.EXISTS); } public FOLDomain getFOLDomain() { return domain; } @Override public Token nextToken() { int startPosition = getCurrentPositionInInput(); if (lookAhead(1) == '(') { consume(); return new Token(LogicTokenTypes.LPAREN, "(", startPosition); } else if (lookAhead(1) == ')') { consume(); return new Token(LogicTokenTypes.RPAREN, ")", startPosition); } else if (lookAhead(1) == ',') { consume(); return new Token(LogicTokenTypes.COMMA, ",", startPosition); } else if (identifierDetected()) { // System.out.println("identifier detected"); return identifier(); } else if (Character.isWhitespace(lookAhead(1))) { consume(); return nextToken(); } else if (lookAhead(1) == (char) -1) { return new Token(LogicTokenTypes.EOI, "EOI", startPosition); } else { throw new LexerException("Lexing error on character " + lookAhead(1)+" at position "+getCurrentPositionInInput(), getCurrentPositionInInput()); } } private Token identifier() { int startPosition = getCurrentPositionInInput(); StringBuffer sbuf = new StringBuffer(); while ((Character.isJavaIdentifierPart(lookAhead(1))) || partOfConnector()) { sbuf.append(lookAhead(1)); consume(); } String readString = new String(sbuf); // System.out.println(readString); if (connectors.contains(readString)) { return new Token(LogicTokenTypes.CONNECTIVE, readString, startPosition); } else if (quantifiers.contains(readString)) { return new Token(LogicTokenTypes.QUANTIFIER, readString, startPosition); } else if (domain.getPredicates().contains(readString)) { return new Token(LogicTokenTypes.PREDICATE, readString, startPosition); } else if (domain.getFunctions().contains(readString)) { return new Token(LogicTokenTypes.FUNCTION, readString, startPosition); } else if (domain.getConstants().contains(readString)) { return new Token(LogicTokenTypes.CONSTANT, readString, startPosition); } else if (isVariable(readString)) { return new Token(LogicTokenTypes.VARIABLE, readString, startPosition); } else if (readString.equals("=")) { return new Token(LogicTokenTypes.EQUALS, readString, startPosition); } else { throw new LexerException("Lexing error on character " + lookAhead(1) + " at position "+getCurrentPositionInInput(), getCurrentPositionInInput()); } } private boolean isVariable(String s) { return (Character.isLowerCase(s.charAt(0))); } private boolean identifierDetected() { return (Character.isJavaIdentifierStart(lookAhead(1))) || partOfConnector(); } private boolean partOfConnector() { return (lookAhead(1) == '=') || (lookAhead(1) == '<') || (lookAhead(1) == '>'); } }