PEGJS谓词语法

时间:2014-10-30 12:22:43

标签: grammar pegjs ambiguous-grammar

我需要在谓词的帮助下创建一个语法。对于给定的情况,以下语法失败。

startRule = a:namespace DOT b:id OPEN_BRACE CLOSE_BRACE {return {"namespace": a, "name": b}}

namespace = id (DOT id)*
DOT = '.';
OPEN_BRACE = '(';
CLOSE_BRACE = ')';
id = [a-zA-Z]+;

作为

的给定输入失败
com.mytest.create();

应该在结果部分中将“create”作为“name”键的值。

任何帮助都会很棒。

1 个答案:

答案 0 :(得分:1)

这里有几件事。

最重要的是,你必须意识到PEG 是贪婪的。这意味着您的(DOT id)*规则会匹配所有DOT ID序列,包括您在startRuleDOT b:id所拥有的序列。

可以使用前瞻解决。

另一件事是您必须记住使用join,因为默认情况下它会将每个字符作为数组的成员返回。

我还添加了分号规则。

试试这个:

start =
  namespace:namespace DOT name:string OPEN_BRACE CLOSE_BRACE SM nl?
    {
      return { namespace : namespace, name : name };
    }

/* Here I'm using the lookahead: (member !OPEN_BRACE)*  */
namespace =
  first:string rest:(member !OPEN_BRACE)* 
    {
      rest = rest.map(function (x) { return x[0]; });
      rest.unshift(first);
      return rest;
    }

member =
  DOT str:string
    { return str; }

DOT =
  '.'

OPEN_BRACE =
  '('

CLOSE_BRACE =
  ')'

SM =
  ';'

nl =
  "\n"

string =
  str:[a-zA-Z]+
    { return str.join(''); }

据我所知,我正在解析该行。