BNF语法有没有结尾的部分?

时间:2015-06-04 07:15:51

标签: c# bnf tinypg

我需要解析一个我没有设计的简单专有语言,因此我无法改变语言。我需要C#中的结果,所以我一直在使用TinyPG因为它易于使用,并且不需要外部库来运行解析器。 TinyPG生成一个简单的LL(1)解析器。

我目前遇到的问题与语言如何将文件分成几个部分有关。它有不同类型变量的部分,设置它们的初始值,方程定义等。我只关心声明变量的部分,所以我想忽略其余部分。我不了解其他部分的所有规则,也不想弄明白。它们可能被视为评论。

这是一个代码示例:

  PARAMETER
    Density             AS REAL
    CrossSectionalArea  AS REAL

 SET # Parameter values
    T101.FO                 := "SimpleEventFOI::dummy";
    T101.CrossSectionalArea := 1    ; # m2

EQUATION
    OutSingleInt = SingleInt;
    OutArrayInt = ArrayInt;

我关心PARAMETER和SET部分,但不关心EQUATION部分。如您所见,问题是这些部分没有END标记。因此,当我得到不同的关键字时,我无法弄清楚如何告诉语法某个部分结束,但新关键字可能会开始一个新的部分。在我的尝试中,新的部分起始关键字被消耗以关闭旧部分。

这里列出的部分比我在这里列出的要多得多,其中一部分是我关心的,有些部分我不是。它们似乎分为两种类型,"看起来像PARAMETER"在陈述结尾处没有分号,"看起来像EQUATION"哪个。这种语言不是大小写或空白敏感的。这些部分可以是任何顺序。 (例如SET,EQUATION,PARAMETER)除了评论之外,整个事情可以写在一行上。

目前我通过使用正则表达式来查找我感兴趣的部分,并且仅将这些部分提供给解析器,但我也遇到了麻烦。正则表达式,适用于所有情况,但不会意外地在评论中选取关键字。我可能最终只是扩展这个解决方案来解决它的问题,但直接在语法中解决问题会更好。这可能不仅仅是LL(1)语言。

1 个答案:

答案 0 :(得分:0)

我尝试了以下tpg代码,它可以解析你的例子。看起来TinyPG无法区分关键字和id,所以我稍微破解了ID。

//Tiny Parser Generator v1.3
//Copyright © Herre Kuijpers 2008-2012

<% @TinyPG Namespace="Test" %>

PARAMETER   -> @"PARAMETER";
SET         -> @"SET";
EQUATION    -> @"EQUATION";

AS          -> @"AS";

ID          -> @"\b(?!(PARAMETER|SET|EQUATION)\b)([a-zA-Z]\w+)";
DOT         -> @"\.";
EQ          -> @":=";
EXPR        -> @"\d|""[^""]*""";
END         -> @";";

[Skip] WS   -> @"\s+|#[^\r\n]+";

EQDECL      -> @"\b(?!(PARAMETER|SET|EQUATION)\b)([^#;]+)";
Equations   -> EQUATION (EQDECL END)*;

Parameters  -> PARAMETER ParamDecl*;
ParamDecl   -> ID AS ID;

Sets        -> SET SetDecl*;
SetDecl     -> FullId EQ EXPR END;
FullId      -> ID DOT ID;

Section     -> Equations | Parameters | Sets;

Start       -> Section*;