Productions
program = cls*;
cls = clsdef name openbrace clsdata closingbrace;
clsdata = (clsfield|clsmethod)*;
clsfield = [variabletype]:name [variablename]:name semi;
clsmethod = [returntype]:name [methodname]:name openmethodbrace closingmethodbrace openbrace closingbrace;问题出在
clsdata = (clsfield|clsmethod)*;如果我将clsdata设置为
clsdata = clsfield*;或转到
clsdata = clsmethod*;但是,正如您可以想象的那样,它工作得很好,它的含义与我想要的并不相同。我想要一个同时支持方法和字段的类(没有特定的顺序!)
所以我的问题是,我应该如何定义clsdata,这样我就不会出错。我可以想到递归的替代方案,但我希望尽可能保持干净!
谢谢
发布于 2011-03-28 20:55:47
clsdata = (clsfield|clsmethod)*;
SableCC具有类似EBNF的语法,但不支持这种类型的语法规则。正如您已经做过的,非终端替代方法clsfield和clsmethod需要重新映射到它们自己的生产环境中。
但我不确定这是不是最好的方法
如果你查看任何一个SableeCC example grammars,你会发现这是定义“类成员”的标准方式。尽管您也许可以通过删除clsmembers来简化语法
Productions
program = cls*;
cls = clsdef name openbrace clsmember* closingbrace;
clsmember = {clsfield} clsfield | {clsmethod} clsmethod;
clsfield = [variabletype]:name [variablename]:name semi;
clsmethod = [returntype]:name [methodname]:name openmethodbrace closingmethodbrace openbrace closingbrace发布于 2011-03-28 09:51:40
这是可行的:
Productions
program = cls*;
cls = clsdef name openbrace clsmembers closingbrace;
clsmembers = clsmember*;
clsmember = {clsfield} clsfield | {clsmethod} clsmethod;
clsfield = [variabletype]:name [variablename]:name semi;
clsmethod = [returntype]:name [methodname]:name openmethodbrace closingmethodbrace openbrace closingbrace;然而,我不确定这是不是最好的方法。我欢迎其他方法!
https://stackoverflow.com/questions/5453780
复制相似问题