java - ANTLR 匹配标识符但不是保留关键字
问题描述
我正在尝试使用不同的符号匹配复数,其中一个使用cis
这样的函数:MODULUS cis
PHASE
问题是我的标识符规则与cis
它后面的数字的开头匹配,并且由于它比CIS
令牌本身大,它总是返回一个标识符令牌类型。我怎么能避免呢?
这是语法:
grammar Sandbox;
input : number? CIS UNSIGNED
| IDENTIFIER
;
number : FLOAT
| UFLOAT
| UINT
| INT
;
fragment DIGIT : [0-9] ;
UFLOAT : UINT (DOT UINT? | 'f') ;
FLOAT : SUB UFLOAT ;
UINT : DIGITS ;
INT : SUB UINT ;
UNSIGNED : UFLOAT
| UINT
;
DIGITS : DIGIT+ ;
// Specific lexer rules
CIS : 'cis' ;
SUB : '-' ;
DOT : '.' ;
WS : [ \t]+ -> skip ;
NEWLINE : '\r'? '\n' ;
IDENTIFIER : [a-zA-Z_]+[a-zA-Z0-9_]* ; // has to be after complex so i or cis doesn't match this first
编辑:我试图解析的输入是复杂的1+i
,但使用它各自的模数和相位,如下所示:1.4142135623730951cis0.7853981633974483
我的实际问题是IDENTIFIER规则匹配cis0
而不是仅仅匹配CIS词法分析器规则,即使它是在它之前定义的。
我隐约知道 ANTLR 根据最大匹配选择规则,但在这种情况下我想避免 =o。
解决方案
我在这里看到两个解决方案:
- 使复数成为单个词法分析器规则:
COMPLEX: (FLOAT | UFLOAT | UINT | INT) WS* CIS WS* UNSIGNED;
这将比标识符或 pur CIS 关键字长(因此首先匹配)。
- 一个
cis
secquence 是一个关键字,当它跟随一个数字时(它们之间有可选的空格),对吧?因此,如果条件为真,您可以在您的谓词中进行回顾LA(-1)
以拒绝作为标识符。cis
我更喜欢解决方案 1,因为约定是单个实体(复数是,如浮点数或字符串,单个逻辑实体)在词法分析器规则中完全匹配,而不是在解析器规则中。
推荐阅读
- linux - 我是否必须重新重建 opencv 才能添加 opencv_contrib?
- java - 可以扫描整数和字符的扫描仪
- php - 有没有办法安装旧的 Laravel-Auditing 版本?
- swift - 斯威夫特:netServiceBrowser didRemoveService MacOSX 10.13
- laravel - 模块的 Laravel 配置文件
- python - TypeError:将熊猫文件保存为文本时,数组dtype('object')和格式说明符('%d %d')`不匹配
- php - SLIM3 - 在自己的类中访问数据库容器
- javascript - 如何在主文件 Index.js 中使用对象参数调用模块
- java - 应用程序更新从内部存储中删除旧的共享首选项数据
- javascript - html CSS Table 从表格中间滚动