这个语法有什么问题? (ANTLRWorks 1.4)
我在 ANTLRWorks 1.4 中编写了以下代码,
grammar hmm;
s : (put_a_in_b)|(put_out_a)|(drop_kick)|(drop_a)|(put_on_a);
put_a_in_b : (PUT_SYN)(ID)(IN_SYN)(ID);
put_out_a : (PUT2_SYN)(OUT_SYN)(ID) | (E1)(ID);
drop_kick : ('drop')('kick')(ID);
drop_a : (DROP_SYN)(ID);
put_on_a : (E2)(ID);
PUT_SYN : 'put' | 'place' | 'drop';
PUT2_SYN : 'put' | 'douse';
IN_SYN : 'in' | 'into' | 'inside' | 'within';
OUT_SYN : 'out';
E1 : 'extinguish'|'douse';
DROP_SYN : 'drop' | 'throw' | 'relinquish';
WS : ( ' ' | '\t' | '\r' | '\n' ) {$channel=HIDDEN;};
ID : ('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'0'..'9'|'_')*;
E2 : 'put on'|'don'|'wear';
COMMENT
: '//' ~('\n'|'\r')* '\r'? '\n' {$channel=HIDDEN;}
| '/*' ( options {greedy=false;} : . )* '*/' {$channel=HIDDEN;}
;
当我使用输入运行它时:
drop object
我收到 MismatchedTokenException(5 != 15)。
通过输入:
put o1 in o2
我得到一个 NoViableAltException。
虽然
place o2 in o2
我对此很陌生,但它运行得很好,但似乎存在歧义?或者我对 ANTLR 的使用不正确?
I have the following code written in ANTLRWorks 1.4
grammar hmm;
s : (put_a_in_b)|(put_out_a)|(drop_kick)|(drop_a)|(put_on_a);
put_a_in_b : (PUT_SYN)(ID)(IN_SYN)(ID);
put_out_a : (PUT2_SYN)(OUT_SYN)(ID) | (E1)(ID);
drop_kick : ('drop')('kick')(ID);
drop_a : (DROP_SYN)(ID);
put_on_a : (E2)(ID);
PUT_SYN : 'put' | 'place' | 'drop';
PUT2_SYN : 'put' | 'douse';
IN_SYN : 'in' | 'into' | 'inside' | 'within';
OUT_SYN : 'out';
E1 : 'extinguish'|'douse';
DROP_SYN : 'drop' | 'throw' | 'relinquish';
WS : ( ' ' | '\t' | '\r' | '\n' ) {$channel=HIDDEN;};
ID : ('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'0'..'9'|'_')*;
E2 : 'put on'|'don'|'wear';
COMMENT
: '//' ~('\n'|'\r')* '\r'? '\n' {$channel=HIDDEN;}
| '/*' ( options {greedy=false;} : . )* '*/' {$channel=HIDDEN;}
;
When I run it with the input:
drop object
I get a MismatchedTokenException(5 != 15).
And with the input :
put o1 in o2
I get a NoViableAltException.
Though it runs fine with
place o2 in o2
I'm new to this, but it seems like there's ambiguities? Or maybe my usage of ANTLR is incorrect?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
您已将
'drop'
和'put'
放入两个不同的词法分析器规则中:当词法分析器遇到
put
时,PUT_SYN
将始终是与其匹配的规则,因此可以(或应该)从PUT2_SYN
规则中删除'put'
。因此,解析字符串
drop object
时出现问题:解析器将尝试匹配drop_a : (DROP_SYN)(ID);
但"drop" 将在词法分析器规则
PUT_SYN
中进行匹配。编辑
这些同义词列表可以更好地制作成解析器规则(而不是词法分析器规则)。这是一个小演示:
在解释以下源代码时:
您将看到 ANTLRWorks 生成以下解析树:
You've put
'drop'
and'put'
in two different lexer-rules:When
put
is encountered by the lexer,PUT_SYN
will always be the rule that matches it, so'put'
could (or should) be removed from thePUT2_SYN
rule.So, your problem with parsing the string
drop object
: the parser will try to matchdrop_a : (DROP_SYN)(ID);
but the"drop"
will be matched in the lexer rulePUT_SYN
.EDIT
Those synonym-lists can be better made into parser rules (instead of lexer-rules). Here's a small demo:
When interpreting the following source:
you'll see ANTLRWorks generate the following parse-tree: