例如:(p∨q)∧(p∨r)→p∨(q∧r)

时间:2019-10-16 05:47:18

标签: lean

精益定理证明的

Section 3.6显示以下内容:

example : p ∨ (q ∧ r) ↔ (p ∨ q) ∧ (p ∨ r) := sorry

由于这涉及iff,因此我们首先从左到右演示一个方向:

example : p ∨ (q ∧ r) → (p ∨ q) ∧ (p ∨ r) :=

    (assume h : p ∨ (q ∧ r),

        or.elim h

            (assume hp : p, 

                show (p ∨ q) ∧ (p ∨ r), from ⟨or.inl hp, or.inl hp⟩)

            (assume hqr : q ∧ r,

                have hq : q, from hqr.left,
                have hr : r, from hqr.right,

                show (p ∨ q) ∧ (p ∨ r), from  ⟨or.inr hq, or.inr hr⟩))

要走另一个方向,我们必须显示:

(p ∨ q) ∧ (p ∨ r) → p ∨ (q ∧ r)

根据本书中到目前为止显示的示例,该示例与众不同之处在于左侧包含了两个 or表达式...看起来好像d必须两次使用or.elim ...

我弄乱了几种方法。这是一个将or.elim嵌套在另一个{

example : (p ∨ q) ∧ (p ∨ r) → p ∨ (q ∧ r) :=

    (assume h : (p ∨ q) ∧ (p ∨ r),

        have hpq : p ∨ q, from h.left,
        have hpr : p ∨ r, from h.right,

        or.elim hpq

            (assume hp : p,

                show p ∨ (q ∧ r), from or.inl hp)

            (assume hq : q, 

                or.elim hpr

                    (assume hp : p,

                        show p ∨ (q ∧ r), from or.inl hp)

                    (assume hr : r,

                        show p ∨ (q ∧ r), from or.inr ⟨hq, hr⟩)))

让我感到奇怪的是,以下表达式出现了两次:

(assume hp : p,

    show p ∨ (q ∧ r), from or.inl hp)

有没有不涉及这种重复的方法?

还有更惯用的方法吗?

1 个答案:

答案 0 :(得分:3)

您的方法使用Theorem Proving In Lean中介绍的第一种方法,并不是真正的惯用语,因为精益数学库中的代码是以战术模式编写的(在书中稍后介绍)或完整的模式。这是一个战术模式证明:

import tactic.rcases -- advanced mathlib tactics, to speed things up a bit
variables (p q r : Prop)

example : (p ∨ q) ∧ (p ∨ r) → p ∨ (q ∧ r) :=
begin
  rintro ⟨hpq,hpr⟩,
  cases hpq, -- this is or.elim
    left, assumption, -- first show
  cases hpr, -- second or.elim
    left, assumption, -- second show
  right, exact ⟨hpq, hpr⟩
end

我也看不到如何避免重复的代码-left, assumption扮演着assume, show的角色。如果要避免导入,可以将rintro行更改为intro h, cases h with hpq hpr,

尽管如此,这种逻辑证明可以很容易地以直接模式编写:

example (p q r : Prop) : (p ∨ q) ∧ (p ∨ r) → p ∨ (q ∧ r) :=
λ ⟨hpq, hpr⟩, or.elim hpq or.inl $ λ hq, or.elim hpr or.inl $ λ hr, or.inr ⟨hq, hr⟩

“复制”现在只是功能or.inl出现两次的事实。我的感觉是,由于p可以用两种不同的方式从假设中得到证明,因此您需要在某个地方进行重复,因为您处在参数的两个不同“线程”中。一旦您了解了Lean的_漏洞功能的强大功能,就不难构建这样的术语。例如,在构造此lambda术语的一半过程中,我的会话如下所示:

example (p q r : Prop) : (p ∨ q) ∧ (p ∨ r) → p ∨ (q ∧ r) :=
λ ⟨hpq, hpr⟩, or.elim hpq or.inl $ _

孔的错误准确地告诉了我我需要构造哪个术语来填补它。

最后,就像@jmc所说的那样,这样的东西可以用策略来伪装,这实际上可能是解决该目标的惯用方式:

import tactic.tauto

example (p q r : Prop): (p ∨ q) ∧ (p ∨ r) → p ∨ (q ∧ r) :=
by tauto!

请注意此处的导入。精益的数学库mathlib(所有的数据都来自此库),数学家在那里做数学,计算机科学家也制定了强大的策略,这使每个人(不仅仅是数学家)生活得更好。

如果您还有其他问题,一种更有效的答案答案是在the Lean chat at Zulip处提问,也许是在#new成员流中。那里的团队通常会非常高效地处理事务。