如何禁用内置规则?

时间:2013-12-05 13:08:30

标签: parsing built-in bnfc

如何禁用所有BNFC内置规则,例如IdentInteger或用于分隔令牌的空格?

我发现他们无用恼人的,因为它们干扰了我正在尝试编写的解析器。

我已经尝试重新定义它们,但似乎词法分析器继续为它们生成规则。我可以从生成的文件中手动删除它们,但我完全反对修改机器生成的代码。


为什么令人讨厌的长版本。

我刚开始学习如何使用BNFC。我尝试的第一件事是将我之前的作品从Alex转换为BNFC。特别是我想只匹配“好”的罗马数字。我觉得这很简单: 罗马数字可以看作像

这样的序列
<thousand-part> <hundred-part> <tens-part> <unit-part>

他们不可能都是空的。因此,数字要么具有非空thousand-part,要么可以是其他数字,或者它是空的thousand-part,因此hundred-tens-或{{1 } unit-必须为非空。同样的事情可以迭代,直到单位的基本情况。

所以我想出了这个,这或多或少是对我在亚历克斯所做的直接翻译:

part

现在,问题在于,如果我尝试构建此解析器,则在提供类似的输入时

N1.            Numeral ::= TokThousands HundredNumber     ;
N2.            Numeral ::= HundredNumberNE                ; --NE = Not Empty
N3.      HundredNumber ::=                                ;
N4.      HundredNumber ::= HundredNumberNE                ;
N5.    HundredNumberNE ::= TokHundreds TensNumber         ;
N6.    HundredNumberNE ::= TensNumberNE                   ;
N7.         TensNumber ::=                                ;
N8.         TensNumber ::= TensNumberNE                   ;
N9.       TensNumberNE ::= TokTens UnitNumber             ;
N10.      TensNumberNE ::= UnitNumberNE                   ;
N11.        UnitNumber ::=                                ;
N12.        UnitNumber ::= UnitNumberNE                   ;
N13.      UnitNumberNE ::= TokUnits                       ;


token TokThousands ({"MMM"} | {"MM"} | {"M"}) ;  -- No x{m,n} in BNFC regexes?
token TokHundreds  ({"CM"} | {"DCCC"} | {"DCC"} | {"DC"} | {"D"} | {"CD"} | {"CCC"} | {"CC"} | {"C"}) ;
token TokTens      ({"IC"} | {"XC"} | {"LXXX"} | {"LXX"} | {"LX"} | {"LX"} | {"L"} | {"IL"} | {"XL"} | {"XXX"} | {"XX"} | {"X"}) ;
token TokUnits     ({"IX"} | {"VIII"} | {"VII"} | {"VI"} | {"V"} | {"IV"} | {"III"} | {"II"} | {"I"}) ;

或者一般来说,如果MMI 中不止一个的数字不为空,则解析器会出错,因为BNFC无法将*-part与单个令牌匹配,因此它使用了内置MMI规则。由于规则没有出现在语法中,因此它会引发一个解析错误,虽然输入字符串完全没有我定义的语法,但它是 bogus Ident规则。

注意:我确认如果我用空格分隔不同的部分,我得到正确的输入,但后来我想把空格分开整数,而不是它们的标记。

1 个答案:

答案 0 :(得分:0)

根据BNFC的documentation

  

这些类型是硬编码的,不能是规则的值类型

这意味着:无需修改生成的代码就无法禁用内置规则。唯一的选择是编写一个脚本,自动从生成的文件中删除伪造的规则,并始终使用Makefile来构建词法分析器和解析器,以避免忘记该步骤。

似乎作者故意决定降低BNFC 强加他们对整数文字的定义的灵活性,标识符应该是什么样的,标记应该如何分开等 他们可能提供了默认规则,允许使用某些选项禁用它们,但他们认为如果您不同意他们的定义,那么您根本不应该使用他们的工具。