【问题标题】:Neat way to distinguish identifiers and variable names (ANTLR)?区分标识符和变量名(ANTLR)的巧妙方法?
【发布时间】:2011-12-02 14:31:33
【问题描述】:

在 ANTLR 语法中,我们如何区分变量名和标识符?

VAR: ('A'..'Z')+ DIGIT*  ;
IDENT  :   ('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'0'..'9'|'_'|'-')*;

语法(在 ANTLR 中)不起作用,因为编译器会抱怨某些输入可能永远无法达到 IDENT。这似乎是编译器编写者的经典之作,The lexer hack

对于 ANTLR 用户,您能告诉我您的巧妙解决方法吗?谢谢

【问题讨论】:

    标签: antlr grammar variable-names


    【解决方案1】:

    zell 写道:

    语法(在 ANTLR 中)不起作用,因为编译器会抱怨某些输入可能永远无法达到 IDENT。

    不,这是不正确的。以下语法:

    grammar T;
    
    parse
      :  .* EOF
      ;
    
    VAR   : ('A'..'Z')+ DIGIT*  ;
    IDENT : ('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'0'..'9'|'_'|'-')*;
    
    fragment DIGIT : '0'..'9';
    

    不会产生任何错误或警告。词法分析器只创建两种类型的标记:

    1. 如果某些内容以一个或多个大写 ascii 字母开头,后跟零个或多个数字,则创建 VAR
    2. 如果某些内容以小写 ascii 字母或下划线开头,后跟 ('a'..'z'|'A'..'Z'|'0'..'9'|'_'|'-')*,则会创建 IDENT

    请注意,IDENT 永远不能以大写的 ascii 字母开头:它总是会变成 VAR

    因此,如果您的解析器规则如下所示:

    foo
      :  IDENT
      ;
    

    并且整个输入是"BAR",那么就会出现解析器错误,因为词法分析器不会生成INDENT 标记,而是生成VAR 标记,即使解析器“要求”IDENT .

    您必须了解,无论解析器向词法分析器提出什么要求,词法分析器都独立于解析器运行。

    【讨论】:

      猜你喜欢
      • 2017-01-07
      • 2013-01-21
      • 1970-01-01
      • 1970-01-01
      • 2011-01-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-12-31
      相关资源
      最近更新 更多