语法条件 `!`(标记为 "except")的作用是什么?
What does the syntax condition `!` (labelled "except") do?
Rascal 语法包含未记录的语法规则产生式:
| except: Sym symbol "!" NonterminalLabel
它在语法上的作用类似于跟随条件,并且在注释为 "conditional" 的部分中。我看到它在 Rascal 语法本身中使用。 NonterminalLabel
用于单独的产生式规则(不是具有所有替代项的产生式)。那么这个条件有什么作用呢?
如果‘E! add' 出现在规则中,那么它只表示 E,但是 E 的标记为 "add" 的规则就好像不存在一样。
此限制仅深入一层,因此递归 E 将再次具有 "add" 规则。
例如:
syntax E
= id: Id
| app: E "(" {E!comma ","}* ")"
> left mul: E "*" E
> left add: E "+" E
> right comma: E "," E
;
函数应用规则{E ","}*
中的E
限制不能是逗号表达式,以避免句法歧义。
- 这里的好处是您不必引入另一个在逻辑上也表示表达式的非终结符。
- 陷阱在于!运算符是一个硬性限制,因此可能使可接受的语言实际上更小:使用!如果不小心使用,可能会导致意外的解析错误。
旁注:!运算符也是用于对优先级 (>) 和关联(左、右)语义建模的原始约束类型,但它们是可传递的并检查安全性等。另一方面,这是对定义的残酷删除,因此可能会改变您的语言接受的句子。
Rascal 语法包含未记录的语法规则产生式:
| except: Sym symbol "!" NonterminalLabel
它在语法上的作用类似于跟随条件,并且在注释为 "conditional" 的部分中。我看到它在 Rascal 语法本身中使用。 NonterminalLabel
用于单独的产生式规则(不是具有所有替代项的产生式)。那么这个条件有什么作用呢?
如果‘E! add' 出现在规则中,那么它只表示 E,但是 E 的标记为 "add" 的规则就好像不存在一样。 此限制仅深入一层,因此递归 E 将再次具有 "add" 规则。
例如:
syntax E
= id: Id
| app: E "(" {E!comma ","}* ")"
> left mul: E "*" E
> left add: E "+" E
> right comma: E "," E
;
函数应用规则{E ","}*
中的E
限制不能是逗号表达式,以避免句法歧义。
- 这里的好处是您不必引入另一个在逻辑上也表示表达式的非终结符。
- 陷阱在于!运算符是一个硬性限制,因此可能使可接受的语言实际上更小:使用!如果不小心使用,可能会导致意外的解析错误。
旁注:!运算符也是用于对优先级 (>) 和关联(左、右)语义建模的原始约束类型,但它们是可传递的并检查安全性等。另一方面,这是对定义的残酷删除,因此可能会改变您的语言接受的句子。