在我的语法中,我希望同时拥有"变量标识符"和"功能标识符"。基本上,我希望对函数标识符中允许的字符限制较少。但是,我遇到的问题是所有变量标识符都是有效的函数标识符。
作为一个例子,假设我想在函数标识符中允许使用大写字母,但在变量标识符中不允许。我目前的(可能是天真的)可能看起来像:
prog : 'func' FunctionId
| 'var' VariableId
;
FunctionId : [a-zA-Z]+ ;
VariableId : [a-z]+ ;
根据上述规则,var hello
无法解析。如果我理解正确,这是因为FunctionId
首先被定义,所以"你好"被视为FunctionId
。
我可以让antlr选择更具体的有效规则吗?
答案 0 :(得分:1)
可以找到解释为什么你的语法不能按预期工作的原因here。
您可以使用语义谓词解决此问题:
AUTH_EXTRA_ARGUMENTS = {'hd': 'example.com'}
在词法分析器级别上只有id。在解析器级别,您可以将id限制为小写字符。 grammar Test;
prog : 'func' functionId
| 'var' variableId
;
functionId : Id;
variableId : {isVariableId(getCurrentToken().getText())}? Id ;
Id : [a-zA-Z]+;
看起来像是:
isVariableId(String)
答案 1 :(得分:1)
我可以让antlr选择更具体的有效规则吗?
否(如前所述)。词法分析器仅匹配尽可能多的匹配,并且在2个或更多规则匹配相同的情况下,首先定义的那个"胜出"。没有办法解决这个问题。
我会这样做:
prog : 'func' functionId
| 'var' variableId
;
functionId : LowerCaseId | UpperCaseId ;
variableId : LowerCaseId ;
LowerCaseId : [a-z]+ ;
UpperCaseId : [A-Z] [a-zA-Z]* ;