鉴于
notation rtranclp ("(_^**)" [1000] 1000)
我可以写一个中缀op ⇒
"op ⇒⇧*⇧* x x'"
但不是更可读和更漂亮
"x ⇒⇧*⇧* x'"
我知道,对于每个具体的关系(在这种情况下为⇒
),我可以为此设置缩写。但我是否也可以解决这个问题,即任何中缀关系?
如果是,我可以将其扩展到多个关系和其他参数吗?例如,给定两个中缀关系⇒
和▹
,以及另一个术语y
我想设置它以便我可以写
x (⇒;▹)⇗y⇖ x'
(注意使用中缀)而不是
foo op ⇒ op ▹ y x x'
(在我的情况下,其类型为foo :: ('a ⇒ 'a ⇒ bool) ⇒ ('a ⇒ 'b ⇒ bool) ⇒ 'b ⇒ 'a ⇒ 'a
)。
答案 0 :(得分:3)
我认为所有中缀关系的通用解决方案是不可能的,因为解析器不会孤立地知道关系符号。从mixfix.ML中的实现可以看出,带有关系符号<
的中缀声明等同于两个mixfix声明,即具有适当优先级的"op <"
和"(_ < _)"
。
然而,除了为谓词和谓词变换器的所有组合引入缩写之外,还有一个更通用和更优雅的解决方案。首先,介绍关系符号的句法类别。要获得正确的输出,请添加语法标记_infix
nonterminal rel
syntax (output) "_infix" :: "rel ⇒ logic" ("_")
然后,声明一个语法常量_rtranclp_rel
,用于中缀与中缀关系。
syntax "_rtranclp_rel" :: "logic ⇒ rel ⇒ logic ⇒ logic" ("(_ _⇧*⇧* _)")
translations "_rtranclp_rel x R y" ⇀ "CONST rtranclp R x y"
translations "_rtranclp_rel x (_infix R) y" ↽ "CONST rtranclp R x y"
现在,为您要与rel
使用的关系_rtranclp_rel
添加语法翻译:
consts rel :: "nat ⇒ nat ⇒ bool" (infix "⇒" 100)
syntax "_rel_infix" :: rel ("⇒")
translations "_rel_infix" ⇀ "CONST rel"
translations "_rel_infix" ↽ "_infix (CONST rel)"
然后,Isabelle应该能够正确地解析和漂亮x ⇒⇧*⇧* z
。但请注意,rtranclp
的所有完全应用的实例都是精美打印的中缀(例如,rtranclp R x y
,与关系是否为中缀符号无关。
此机制适用于您的函数foo
:
consts foo :: "('a ⇒ 'a ⇒ bool) ⇒ ('b ⇒ 'b ⇒ bool) ⇒ 'b ⇒ 'a ⇒ 'a ⇒ bool"
syntax "_foo_rel" :: "logic ⇒ rel ⇒ rel ⇒ logic ⇒ logic ⇒ logic" ("_ '(_;_')⇗_⇖ _")
translations "_foo_rel x R S y z" ⇀ "CONST foo R S x y z"
translations "_foo_rel x (_infix R) (_infix S) y z" ↽ "CONST foo R S x y z"
当然,mixfix注释中的优先级应该调整为合理的注释。甚至可以递归地执行此操作。例如:
syntax "_rtranclp_rel2" :: "rel ⇒ rel" ("_⇧*⇧*")
translations "_rtranclp_rel2 R" ⇀ "CONST rtranclp R"
translations "_rtranclp_rel2 (_infix R)" ↽ "_infix (CONST rtranclp R)"
term "x (⇒⇧*⇧*;⇒)⇗y⇖ z"