[英]ANTLR4: lexer rule for: Any string as long as it doesn't contain these two side-by-side characters?
有什么办法可以在ANTLR4中表达这一点:
任何不包含星号的字符串,只要其后立即带有正斜杠即可?
这不起作用: (~'*/')*
因为ANTRL会引发此错误: multi-character literals are not allowed in lexer sets: '*/'
这可行,但不正确: (~[*/])*
因为它禁止包含单个字符*
或/
的字符串。
我有类似的问题,我的解决方案是: ( ~'*' | ( '*'+ ~[/*]) )* '*'*
。
我能得到的最接近的结果是将测试放入解析器而不是词法分析器中。 这并不是您所要的,但确实可以。
诀窍是在必须针对任何邪恶字符测试的任何字符串之前使用语义谓词。 实际的测试是用Java完成的。
grammar myTest;
@header
{
import java.util.*;
}
@parser::members
{
boolean hasEvilCharacters(String input)
{
if (input.contains("*/"))
{
return false;
}
else
{
return true;
}
}
}
// Mimics a very simple sentence, such as:
// I am clean.
// I have evil char*/acters.
myTest
: { hasEvilCharacters(_input.LT(1).getText()) }? String
(Space { hasEvilCharacters(_input.LT(1).getText()) }? String)*
Period EOF
;
String
: ('A'..'Z' | 'a'..'z')+
;
Space
: ' '
;
Period
: '.'
;
通过NetBeans 8.0.1中ANTLRWorks 2中的TestRig在ANTLR 4.4中进行了测试。
如果不允许的序列很少,那么存在没有解析器/词法分析器动作的解决方案:
grammar NotParser;
program
: (starslash | notstarslash)+
;
notstarslash
: NOT_STAR_SLASH
;
starslash
: STAR_SLASH
;
STAR_SLASH
: '*'+ '/'
;
NOT_STAR_SLASH
: (F_NOT_STAR_SLASH | F_STAR_NOT_SLASH) +
;
fragment F_NOT_STAR_SLASH
: ~('*'|'/')
;
fragment F_STAR_NOT_SLASH
: '*'+ ~('*'|'/')
| '*'+ EOF
| '/'
;
这个想法是组成
有一些处理特殊情况的规则(多个' '后跟'/'或尾随' ')
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.