有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java在ANTLR BNF语法符号中epsilon的等价物是什么?

在利用ANTLR 3.3的过程中,我将修改当前语法,以支持不带括号的输入。以下是我语法的第一个版本:

grammar PropLogic;

        NOT : '!' ;
        OR  : '+' ;
        AND : '.' ;
        IMPLIES : '->' ;
        SYMBOLS : ('a'..'z') | '~' ;
        OP : '(' ;
        CP : ')' ;

    prog    : formula EOF ;


    formula : NOT formula
        | OP formula( AND formula CP | OR formula CP | IMPLIES formula CP)
        | SYMBOLS ;


    WHITESPACE : ( '\t' | ' ' | '\r' | '\n'| '\u000C' )+    { $channel = HIDDEN; } ;

然后我将其更改为支持适当的功能:

grammar PropLogic;

    NOT : '!' ;
    OR  : '+' ;
    AND : '.' ;
    IMPLIES : '->' ;
    SYMBOL : ('a'..'z') | '~' ;
    OP : '(' ;
    CP : ')' ;
    EM : '' ;

prog    : formula EOF ;


formula : OP formula( AND formula CP | OR formula CP | IMPLIES formula CP)
    | ( NOT formula | SYMBOL )( AND formula | OR formula | IMPLIES formula | EM ) ;


WHITESPACE : ( '\t' | ' ' | '\r' | '\n'| '\u000C' )+    { $channel = HIDDEN; } ;

但我一直面临以下错误:

error<100>:  syntax error: invalid char literal: ''
error<100>:  syntax error: invalid char literal: ''

有人知道我该如何克服这个错误吗


共 (2) 个答案

  1. # 1 楼答案

    您的EM令牌:

    EM : '' ;
    

    无效:无法匹配lexer规则中的空字符串

    要匹配epsilon(无),您应该执行以下操作:

    rule 
      :  A 
      |  B 
      |  /* epsilon */ 
      ;
    

    当然,可以安全地删除注释/* epsilon */

    请注意,在当前语法中这样做时,ANTLR会抱怨使用多个选项可以匹配规则。这是因为你的语法模棱两可

  2. # 2 楼答案

    我不是ANTLR专家,但你可以试试:

    formula : term ((AND | OR | IMPLIES ) term )*;
    term :  OP formula CP | NOT term | SYMBOL ;
    

    如果你想使用传统的运算符优先级,这是行不通的,但这是另一个问题

    编辑:OP提高了赌注;他也想要优先权。我会让他半途而废,因为这不是我的一部分 关于最初的问题。我在语法中增加了优先权,使之成为一种暗示 优先级比其他运算符低,剩下的由OP来决定

     formula:  disjunction ( IMPLIES disjunction )* ;
     disjunction:  term (( AND | OR ) term )* ;
     term:  OP formula CP | NOT term | SYMBOL ;
    

    OP还问,“如何将(!p或q)转换为p->;q”。我想他应该 我已经把这作为一个单独的问题问了。然而,我已经在这里了。 他需要做的是在树上行走,寻找他不知道的模式 比如,把树换成他喜欢的树,然后把答案打印出来。 这一切都可以通过ANTLR实现,这也是部分原因 它很受欢迎

    实际上,按程序遍历树并检查节点 类型,并将旧节点拼接到新节点是可行的,但这是一个皇家皮塔。 特别是如果你想做很多转换

    更有效的方法是使用 program transformation system,它允许表达表面语法模式以进行匹配和替换。程序转换系统当然包括解析机制,更强大的机制可以让你(甚至坚持)定义 前面的语法和你对ANTLR的理解差不多

    我们的DMS Software Reengineering Toolkit就是这样一个程序转换工具,并且有一个适当定义的命题语法, 以下DMS转换规则将执行OP的附加请求:

    domain proplogic; // tell DMS to use OP's definition of logic as a grammar
    
    rule normalize_implies_from_or( p: term, q: term): formula -> formula
      " NOT \p OR \q " -> " \p IMPLIES \q ";
    

    “…”是“域表示法”,例如,proplogic域的表面语法,“\”是元转义, 所以“\p”和“\q”代表proplogic语法中任意的术语。请注意,应用规则时必须达到“跨”优先级,因为“NOT\p或\q”不是公式,而“\p暗示\q”是;DMS负责所有这些(“公式->;公式”符号是DMS知道该做什么的方式)。此规则进行树到树的重写。生成的树可以通过DMS进行预打印

    你可以看到一个非常类似的例子,例如a grammar for conventional algebra and rewrite rule to simplify algebraic equations