如果我有这样的谓词:
Inductive foo : nat -> nat -> Prop :=
| Foo : forall n, foo n n.
然后我可以简单地使用归纳法来证明一些虚拟引理:
Lemma foo_refl : forall n n',
foo n n' -> n = n'.
Proof.
intros.
induction H.
reflexivity.
Qed.
但是,对于具有产品类型参数的谓词:
Inductive bar : (nat * nat) -> (nat * nat) -> Prop :=
| Bar : forall n m, bar (n, m) (n, m).
几乎相同引理的类似证明被卡住了,因为所有关于变量的假设都消失了:
Lemma bar_refl : forall n n' m m',
bar (n, m) (n', m') -> n = n'.
Proof.
intros.
induction H.
(* :( *)
为什么会这样?如果我用 替换induction
,inversion
那么它的行为符合预期。
引理仍然可以证明,induction
但需要一些解决方法:
Lemma bar_refl : forall n n' m m',
bar (n, m) (n', m') -> n = n'.
Proof.
intros.
remember (n, m) as nm.
remember (n', m') as n'm'.
induction H.
inversion Heqnm. inversion Heqn'm'. repeat subst.
reflexivity.
Qed.
不幸的是,这种方式的证明变得非常混乱,并且对于更复杂的谓词是不可能遵循的。
一个明显的解决方案是这样声明bar
:
Inductive bar' : nat -> nat -> nat -> nat -> Prop :=
| Bar' : forall n m, bar' n m n m.
这解决了所有问题。然而,就我的目的而言,我发现以前的(“元组”)方法更加优雅。有没有办法保持谓词不变并且仍然能够进行可管理的归纳证明?问题甚至来自哪里?