在包含局部变量

时间:2018-02-01 17:40:52

标签: coq ltac

我的目标是在匹配分支中包含对某个引理foo的调用。该调用使用分支本地变量R作为其参数之一:

| SomeConstr => fun R => .... (foo a b c R) ....

我想在foo上执行beta扩展,以便调用成为:

| SomeConstr => fun R => .... ((fun d => foo a b c d) R) ....

这将允许我进一步推广(fun d => foo a b c d),这不会孤独地依赖于分支的本地变量。由于我正在处理非常大的证据,我想用Ltac写这个。这是一次尝试:

match goal with
| [ |- context[(foo ?A ?B ?C ?R)] ] =>
  let d := fresh "d" in
  replace (foo A B C R) with ((fun d => foo A B C d) R)
end.

然而,这与#34;匹配"没有匹配条款失败。如果我用match替换idtac分支的主体,它仍然失败,所以问题显然是由于未能匹配给定的表达式。但是,如果我匹配一个参数,则匹配成功。例如:

match goal with
| [ |- context[(foo ?A ?B ?C)] ] =>
  idtac A; idtac B; idtac C
end.

打印" a"," b"和" c"在连续的线条。我也可以说:

match goal with
| [ |- context[(foo ?A ?B ?C)] ] =>
  let d := fresh "d" in
  replace (foo A B C) with (fun d => foo A B C d) by auto
end.

并且这成功了,但有趣的是,目标仍然没有变化,即。该呼叫仍采用(foo a b c R)而非((fun d => foo a b c d) R)的格式。我在这里做错了什么?

1 个答案:

答案 0 :(得分:7)

replace策略执行β减少。您可以通过编写

来看到这一点
Goal True.
  replace True with ((fun x => x) True) by auto.

如果您改为使用change策略(只有在replace可以解决reflexivity的副条件时才有效),那么它应该有效。例如,

Goal True.
  change True with ((fun x => x) True).

将目标更改为(fun x : Prop => x) True

这是没有记录的,我已将其报告为an issue on GitHub