Built with doc-gen4, running Lean4. Bubbles () indicate interactive fragments: hover for details, tap to reveal contents. Use Ctrl+↑Ctrl+↓to navigate, Ctrl+🖱️to focus. On Mac, use Cmdinstead of Ctrl.
import Mathlib

/-!
# Propositions as Types

* We can represent propositions as types, or interpret (slightly restricted) types as propositions. 
* A proof of a proposition is a term of the corresponding type.
* Defining and proving are essentially the same thing.
* The same foundational rules let us construct propostions and proofs as well as terms and types.
-/

/-!
## Main correspondence

* `A → B` is functions from `A` to `B` as well as `A` implies `B`.
* Function application is the same as *modus ponens*.
* So if we have propositions `A` and `B`, we can construct a proposition `A → B` corresponding to implication.
-/

universe u

def 
functionApplication: {A B : Type u} → (AB) → AB
functionApplication
{
A: Type u
A
B: Type u
B
:
Type u: Type (u+1)
Type u
} (
f: AB
f
:
A: Type u
A
B: Type u
B
) (
a: A
a
:
A: Type u
A
) :
B: Type u
B
:=
f: AB
f
a: A
a
def
modus_ponens: ∀ {A B : Prop}, (AB) → AB
modus_ponens
{
A: Prop
A
B: Prop
B
:
Prop: Type
Prop
} (
h₁: AB
h₁
:
A: Prop
A
B: Prop
B
) (
h₂: A
h₂
:
A: Prop
A
) :
B: Prop
B
:=
h₁: AB
h₁
h₂: A
h₂
/-! ## Other Combination * `A ∧ B` is the conjunction of `A` and `B`. * `A ∨ B` is the disjunction of `A` and `B`. * `¬ A` is the negation of `A`. All these can be constructed by our rules. -/
And (a b : Prop) : Prop
And: PropPropProp
And
Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)
Prod: Type u → Type v → Type (maxuv)
Prod
/-! ## Conjuction and Product ```lean structure And (a b : Prop) : Prop where /-- `And.intro : a → b → a ∧ b` is the constructor for the And operation. -/ intro :: /-- Extract the left conjunct from a conjunction. `h : a ∧ b` then `h.left`, also notated as `h.1`, is a proof of `a`. -/ left : a /-- Extract the right conjunct from a conjunction. `h : a ∧ b` then `h.right`, also notated as `h.2`, is a proof of `b`. -/ right : b ``` This is the same as the product type: ```lean structure Prod (α : Type u) (β : Type v) where /-- The first projection out of a pair. if `p : α × β` then `p.1 : α`. -/ fst : α /-- The second projection out of a pair. if `p : α × β` then `p.2 : β`. -/ snd : β ``` -/ inductive
MyOr: PropPropProp
MyOr
(
A: Prop
A
B: Prop
B
:
Prop: Type
Prop
) :
Prop: Type
Prop
|
inl: ∀ {A B : Prop}, AMyOr A B
inl
:
A: Prop
A
MyOr: PropPropProp
MyOr
A: Prop
A
B: Prop
B
|
inr: ∀ {A B : Prop}, BMyOr A B
inr
:
B: Prop
B
MyOr: PropPropProp
MyOr
A: Prop
A
B: Prop
B
Or (a b : Prop) : Prop
Or: PropPropProp
Or
Sum.{u, v} (α : Type u) (β : Type v) : Type (max u v)
Sum: Type u → Type v → Type (maxuv)
Sum
/-! # Disjunction and Sum ```lean inductive Or (a b : Prop) : Prop where /-- `Or.inl` is "left injection" into an `Or`. If `h : a` then `Or.inl h : a ∨ b`. -/ | inl (h : a) : Or a b /-- `Or.inr` is "right injection" into an `Or`. If `h : b` then `Or.inr h : a ∨ b`. -/ | inr (h : b) : Or a b ``` This is the same as the sum type: ```lean inductive Sum (α : Type u) (β : Type v) where /-- Left injection into the sum type `α ⊕ β`. If `a : α` then `.inl a : α ⊕ β`. -/ | inl (val : α) : Sum α β /-- Right injection into the sum type `α ⊕ β`. If `b : β` then `.inr b : α ⊕ β`. -/ | inr (val : β) : Sum α β ``` -/
True : Prop
True: Prop
True
False : Prop
False: Prop
False
/-! ## True and False These are analogues of `Unit` and `Empty`: ```lean inductive True : Prop where /-- `True` is true, and `True.intro` (or more commonly, `trivial`) is the proof. -/ | intro : True inductive False : Prop ``` -/ /-! ## Negation The negation of a type (or proposition) `A` is `¬ A`, which is the type (or proposition) `A → False`. -/ theorem
everything_implies_true: ∀ (A : Prop), ATrue
everything_implies_true
(
A: Prop
A
:
Prop: Type
Prop
) :
A: Prop
A
True: Prop
True
:= fun
_: ?m.171
_
=>
True.intro: True
True.intro
theorem
false_implies_everything: ∀ (A : Prop), FalseA
false_implies_everything
(
A: Prop
A
:
Prop: Type
Prop
) :
False: Prop
False
A: Prop
A
:= fun
h: ?m.184
h
=> nomatch
h: ?m.184
h
False.rec.{u} (motive : False → Sort u) (t : False) : motive t
False.rec: (motive : FalseSort u) → (t : False) → motive t
False.rec
-- False.rec.{u} (motive : False → Sort u) (t : False) : motive t
False.rec fun x => 1 = 2 : False → 1 = 2
False.rec: ∀ (motive : FalseSort ?u.214) (t : False), motive t
False.rec
(motive := fun
_: ?m.221
_
=>
1: ?m.225
1
=
2: ?m.241
2
) -- False → 1 = 2
example: ∀ {A B : Prop}, ABA
example
{
A: Prop
A
B: Prop
B
:
Prop: Type
Prop
}:
A: Prop
A
B: Prop
B
A: Prop
A
:= fun
a: ?m.324
a
_: ?m.327
_
a: ?m.324
a
Iff (a b : Prop) : Prop
Iff: PropPropProp
Iff
/-! ## If and only if ```lean structure Iff (a b : Prop) : Prop where /-- If `a → b` and `b → a` then `a` and `b` are equivalent. -/ intro :: /-- Modus ponens for if and only if. If `a ↔ b` and `a`, then `b`. -/ mp : a → b /-- Modus ponens for if and only if, reversed. If `a ↔ b` and `b`, then `a`. -/ mpr : b → a ``` -/
example: ∀ {A B : Prop}, (A B) = ((AB) (BA))
example
{
A: Prop
A
B: Prop
B
:
Prop: Type
Prop
}: (
A: Prop
A
B: Prop
B
) = ((
A: Prop
A
B: Prop
B
) ∧ (
B: Prop
B
A: Prop
A
)) :=

Goals accomplished! 🐙
A, B: Prop


(A B) = ((AB) (BA))
A, B: Prop


a
(A B) (AB) (BA)
A, B: Prop


(A B) = ((AB) (BA))
A, B: Prop


a.mp
(A B) → (AB) (BA)
A, B: Prop


a.mpr
(AB) (BA) → (A B)
A, B: Prop


(A B) = ((AB) (BA))
A, B: Prop


(A B) → (AB) (BA)
A, B: Prop

h: A B


(AB) (BA)
A, B: Prop


(A B) → (AB) (BA)
A, B: Prop

h: A B


left
AB
A, B: Prop

h: A B


right
BA
A, B: Prop


(A B) → (AB) (BA)
A, B: Prop

h: A B


left
AB
A, B: Prop

h: A B


right
BA

Goals accomplished! 🐙
A, B: Prop


(A B) → (AB) (BA)
A, B: Prop

h: A B


right
BA

Goals accomplished! 🐙
A, B: Prop


(A B) = ((AB) (BA))
A, B: Prop


(AB) (BA) → (A B)
A, B: Prop

h: (AB) (BA)


A B
A, B: Prop


(AB) (BA) → (A B)
A, B: Prop

h: (AB) (BA)


mp
AB
A, B: Prop

h: (AB) (BA)


mpr
BA
A, B: Prop


(AB) (BA) → (A B)
A, B: Prop

h: (AB) (BA)


mp
AB
A, B: Prop

h: (AB) (BA)


mpr
BA

Goals accomplished! 🐙
A, B: Prop


(AB) (BA) → (A B)
A, B: Prop

h: (AB) (BA)


mpr
BA

Goals accomplished! 🐙
/-! ## Universal Quantifiers * A proposition associated to each term of a type `A` is a function `A → Prop`. * The propostion `∀ x : A, P x` is the proposition that `P x` is true for all `x : A`, which is the dependent function type `(x: A) → P x`. -/
Exists.{u} {α : Sort u} (p : α → Prop) : Prop
Exists: {α : Sort u} → (αProp) → Prop
Exists
/-! ## Existential Quantifiers ```lean inductive Exists {α : Sort u} (p : α → Prop) : Prop where /-- Existential introduction. If `a : α` and `h : p a`, then `⟨a, h⟩` is a proof that `∃ x : α, p x`. -/ | intro (w : α) (h : p w) : Exists p ``` -/
Nat.le (n a✝ : ℕ) : Prop
Nat.le: Prop
Nat.le
Eq.{u_1} {α : Sort u_1} (a✝a✝¹ : α) : Prop
Eq: {α : Sort u_1} → ααProp
Eq
/-! ## Basic types We have seen `≤` can be constructed as indexed inductive type: ```lean inductive Nat.le (n : Nat) : Nat → Prop /-- Less-equal is reflexive: `n ≤ n` -/ | refl : Nat.le n n /-- If `n ≤ m`, then `n ≤ m + 1`. -/ | step {m} : Nat.le n m → Nat.le n (succ m) ``` The equality type is also indexed inductive type: ```lean inductive Eq : α → α → Prop where /-- `Eq.refl a : a = a` is reflexivity, the unique constructor of the equality type. See also `rfl`, which is usually used instead. -/ | refl (a : α) : Eq a a ``` -/
example: ∀ {α β : Type} {f g : αβ} (x y : α), f = gx = yf x = g y
example
{
α: Type
α
β: Type
β
:
Type: Type 1
Type
}{
f: αβ
f
g: αβ
g
:
α: Type
α
β: Type
β
} (
x: α
x
y: α
y
:
α: Type
α
):
f: αβ
f
=
g: αβ
g
x: α
x
=
y: α
y
f: αβ
f
x: α
x
=
g: αβ
g
y: α
y
:=

Goals accomplished! 🐙
α, β: Type

f, g: αβ

x, y: α


f = gx = yf x = g y
α, β: Type

f, g: αβ

x, y: α

hfg: f = g

hxy: x = y


f x = g y
α, β: Type

f, g: αβ

x, y: α


f = gx = yf x = g y
α, β: Type

f, g: αβ

x, y: α

hfg: f = g

hxy: x = y


f x = g y
α, β: Type

f✝, g: αβ

x✝, y: α

hfg: f✝ = g

hxy: x✝ = y

f: αβ

x: α


f x = f x
α, β: Type

f, g: αβ

x, y: α

hfg: f = g

hxy: x = y


f x = g y

Goals accomplished! 🐙