use of com.googlecode.aviator.runtime.type.string.StringSegment in project aviatorscript by killme2008.
the class AviatorEvaluatorInstance method compileStringSegments.
/**
* Compile a string to string segments, if string doesn't have a interpolation,returns an empty
* list.
*
* @param lexeme
* @param sourceFile
* @param lineNo;
* @return
*/
public StringSegments compileStringSegments(final String lexeme, final String sourceFile, final int lineNo) {
List<StringSegment> segs = new ArrayList<StringSegment>();
boolean hasInterpolationOrEscaped = false;
StringCharacterIterator it = new StringCharacterIterator(lexeme);
char ch = it.current(), prev = StringCharacterIterator.DONE;
int lastInterPos = 0;
int i = 1;
for (; ; ) {
if (ch == '#') {
if (prev == '\\') {
// # is escaped, skip the backslash.
final String segStr = lexeme.substring(lastInterPos, i - 2);
segs.add(new LiteralSegment(segStr));
lastInterPos = i - 1;
hasInterpolationOrEscaped = true;
} else {
// # is not escaped.
prev = ch;
ch = it.next();
i++;
if (ch == '{') {
// Find a interpolation position.
if (i - 2 > lastInterPos) {
final String segStr = lexeme.substring(lastInterPos, i - 2);
segs.add(new LiteralSegment(segStr));
}
try {
ExpressionLexer lexer = new ExpressionLexer(this, lexeme.substring(i));
lexer.setLineNo(lineNo);
ExpressionParser parser = new ExpressionParser(this, lexer, newCodeGenerator(sourceFile, false));
Expression exp = parser.parse(false);
final Token<?> lookhead = parser.getLookhead();
if (lookhead == null || (lookhead.getType() != TokenType.Char || ((CharToken) lookhead).getCh() != '}')) {
parser.reportSyntaxError("expect '}' to complete string interpolation");
}
int expStrLen = lookhead.getStartIndex() + 1;
while (expStrLen-- > 0) {
prev = ch;
ch = it.next();
i++;
}
Token<?> previousToken = null;
if (parser.getParsedTokens() == 2 && (previousToken = parser.getPrevToken()) != null && previousToken.getType() == TokenType.Variable) {
// special case for inline variable.
if (previousToken == Variable.TRUE) {
segs.add(new LiteralSegment("true"));
} else if (previousToken == Variable.FALSE) {
segs.add(new LiteralSegment("false"));
} else if (previousToken == Variable.NIL) {
segs.add(new LiteralSegment("null"));
} else {
segs.add(new VarSegment(parser.getSymbolTable().reserve(previousToken.getLexeme()).getLexeme()));
}
} else {
segs.add(new ExpressionSegment(exp));
}
hasInterpolationOrEscaped = true;
lastInterPos = i;
} catch (Throwable t) {
throw new CompileExpressionErrorException("Fail to compile string interpolation: " + lexeme, t);
}
// End of interpolation
}
// End of # is not escaped.
}
}
if (ch == StringCharacterIterator.DONE) {
if (i - 1 > lastInterPos) {
final String segStr = lexeme.substring(lastInterPos, i - 1);
segs.add(new LiteralSegment(segStr));
}
break;
}
prev = ch;
ch = it.next();
i++;
}
if (hasInterpolationOrEscaped) {
return new StringSegments(segs, lexeme.length() * 2 / 3);
} else {
return new StringSegments(Collections.<StringSegment>emptyList(), 0);
}
}
Aggregations