compiling and tutorial world approx finished
This commit is contained in:
18
Game.lean
18
Game.lean
@@ -1,15 +1,15 @@
|
||||
import GameServer.Commands
|
||||
|
||||
import Game.Levels.Tutorial
|
||||
--import Game.Levels.Addition
|
||||
--import Game.Levels.Multiplication
|
||||
--import Game.Levels.Power
|
||||
--import Game.Levels.Function
|
||||
--import Game.Levels.Proposition
|
||||
--import Game.Levels.AdvProposition
|
||||
--import Game.Levels.AdvAddition
|
||||
--import Game.Levels.AdvMultiplication
|
||||
----import Game.Levels.Inequality
|
||||
import Game.Levels.Addition
|
||||
-- import Game.Levels.Multiplication
|
||||
-- import Game.Levels.Power
|
||||
-- import Game.Levels.Function
|
||||
-- import Game.Levels.Proposition
|
||||
-- import Game.Levels.AdvProposition
|
||||
-- import Game.Levels.AdvAddition
|
||||
-- import Game.Levels.AdvMultiplication
|
||||
--import Game.Levels.Inequality
|
||||
|
||||
Title "Natural Number Game"
|
||||
Introduction
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import Game.Levels.Addition.Level_4
|
||||
import Game.MyNat.DecidableEq
|
||||
|
||||
|
||||
World "Addition"
|
||||
@@ -7,9 +8,6 @@ Title "succ_eq_add_one"
|
||||
|
||||
open MyNat
|
||||
|
||||
-- NOTE: this was `one_eq_succ_zero` but we need it earlier.
|
||||
axiom MyNat.one_eq_succ_zero' : (1 : ℕ) = succ 0
|
||||
|
||||
Introduction
|
||||
"
|
||||
I've just added `one_eq_succ_zero` (a proof of `1 = succ 0`)
|
||||
|
||||
@@ -76,7 +76,6 @@ $a + b + c = a + c + b$."
|
||||
rfl
|
||||
|
||||
LemmaTab "Add"
|
||||
NewTactic simp -- TODO: Do we want it to be unlocked here?
|
||||
|
||||
Conclusion
|
||||
"
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
import Game.Levels.Tutorial.L01rfl
|
||||
import Game.Levels.Tutorial.L02rw
|
||||
import Game.Levels.Tutorial.L03rw_practice
|
||||
import Game.Levels.Tutorial.L04one
|
||||
|
||||
import Game.Levels.Tutorial.L04onetwothree
|
||||
import Game.Levels.Tutorial.L05add_zero
|
||||
import Game.Levels.Tutorial.L06add_succ
|
||||
|
||||
World "Tutorial"
|
||||
Title "Tutorial World"
|
||||
|
||||
@@ -13,19 +13,27 @@ NewLemma MyNat.one_eq_succ_zero
|
||||
|
||||
Introduction
|
||||
"
|
||||
The goals of the previous levels in the tutorial mentioned things like addition and multiplication of numbers. But now we start the game itself: building the natural numbers from scratch. Giuseppe Peano defined these numbers via three axioms:
|
||||
The goals of the previous levels in the tutorial mentioned things like addition and
|
||||
multiplication of numbers. But now we start the game itself: building the natural
|
||||
numbers from scratch. Giuseppe Peano defined these numbers via three axioms:
|
||||
|
||||
* `0` is a number.
|
||||
* If `n` is a number, then the *successor* `succ n` of `n` (that is, the number after `n`) is a number.
|
||||
* That's it.
|
||||
|
||||
\"That's it\" means \"there is no other way to make numbers\". More on this later: we need to make sure we've cracked the basics before we start talking about infinity. First let's see if we can count to five.
|
||||
\"That's it\" means \"there is no other way to make numbers\". More on this later: we need to
|
||||
make sure we've cracked the basics before we start talking about infinity. First let's see if we
|
||||
can count to five.
|
||||
|
||||
# Does this make a section?
|
||||
|
||||
What kind of numbers can we make from Peano's axioms? Well, Peano gives us the number `0` and the function `succ` taking numbers to numbers. We could apply the function to the number and then get a new number `succ 0`, and we could name this number `1`. The theorem `one_eq_succ_zero` says that `1 = succ 0`.
|
||||
What kind of numbers can we make from Peano's axioms? Well, Peano gives us the number `0` and the
|
||||
function `succ` taking numbers to numbers. We could apply the function to the number and then get a
|
||||
new number `succ 0`, and we could name this number `1`. The theorem `one_eq_succ_zero` says that
|
||||
`1 = succ 0`.
|
||||
|
||||
We could define `2` to either be `succ 1` or `succ (succ 0)`. Are these two choices definitely equal? Let's see if we can prove it.
|
||||
We could define `2` to either be `succ 1` or `succ (succ 0)`. Are these two choices definitely
|
||||
equal? Let's see if we can prove it.
|
||||
"
|
||||
Statement
|
||||
"$\\operatorname{succ}(1)=\\operatorname{succ}(\\operatorname{succ}(0))$."
|
||||
90
Game/Levels/Tutorial/L05add_zero.lean
Normal file
90
Game/Levels/Tutorial/L05add_zero.lean
Normal file
@@ -0,0 +1,90 @@
|
||||
import Game.Metadata
|
||||
import Game.MyNat.Addition
|
||||
|
||||
|
||||
World "Tutorial"
|
||||
Level 5
|
||||
Title "addition"
|
||||
|
||||
open MyNat
|
||||
|
||||
Introduction
|
||||
"
|
||||
Peano defined addition $a + b$ by adding two axioms to his system.
|
||||
Peano's first axiom was called `add_zero`. Here it is:
|
||||
|
||||
* `add_zero : ∀ (a : ℕ), a + 0 = a`
|
||||
|
||||
In words, the theorem says that if `a` is an arbitrary natural number, then `a + 0 = a`.
|
||||
Another way to think of `add_zero` is as a function, which eats a natural number `a`
|
||||
and returns a proof `add_zero a` of `a + 0 = a`.
|
||||
|
||||
Let me show you how to use Lean's simplifier `simp`
|
||||
to do a lot of work for us."
|
||||
|
||||
LemmaDoc MyNat.add_zero as "add_zero" in "Add"
|
||||
"One of the two axioms defining addition. It says `n + 0 = n`."
|
||||
|
||||
namespace MyNat
|
||||
|
||||
TacticDoc simp "The simplifier. `rw` on steroids.
|
||||
|
||||
A bunch of lemmas like `add_zero : ∀ a, a + 0 = a`
|
||||
are tagged with the `@[simp]` tag. If the `simp` tactic
|
||||
is run by the user, the simplifier will try and rewrite
|
||||
as many of the lemmas tagged `@[simp]` as it can.
|
||||
|
||||
`simp` is a *finishing tactic*. After you run `simp`,
|
||||
the goal should be closed. If it is not, it is best
|
||||
practice to write `simp?` instead and then replace the
|
||||
output with the appropriate `simp only` call. Inappropriate
|
||||
use of `simp` can make for very slow code.
|
||||
"
|
||||
NewTactic simp -- TODO: Do we want it to be unlocked here?
|
||||
|
||||
Statement
|
||||
"$(a+(0+0)+(0+0+0)=a.$"
|
||||
(a : ℕ) : (a + (0 + 0)) + (0 + 0 + 0) = a := by
|
||||
Hint "I want this to say \"Walkthrough\".
|
||||
|
||||
This is an annoying goal. One of rw [add_zero a]` amd `rw [add_zero 0]`
|
||||
will work, but not the other. Can you figure out which? Try the one
|
||||
that works."
|
||||
Branch
|
||||
rw [add_zero 0]
|
||||
Hint "Walkthrough: Now `rw [add_zero a]` will work, so try that next."
|
||||
rw [add_zero a]
|
||||
Hint "OK this is getting old really quickly. And if we have to type
|
||||
weird stuff like `rw [add_zero (a + 0)]` it will be even worse.
|
||||
Fortunately `rw` can do smart rewriting. Go back to the very start
|
||||
of this proof with \"undo\" and try `repeat rw [add_zero]`
|
||||
"
|
||||
Branch
|
||||
repeat rw [add_zero]
|
||||
Hint "`rw` can rewrite proofs of the form `? + 0 = ?`
|
||||
where `?` is arbitrary, and it will just use the
|
||||
first solution which matches for `?`.
|
||||
|
||||
The rest of he proof is easy, but don't finish yet, there's more.
|
||||
|
||||
Lean's simplifier is a tool which does repeated
|
||||
rewriting. And `add_zero` is a `simp` lemma. So go back to the
|
||||
start again and just try `simp`."
|
||||
simp
|
||||
|
||||
NewLemma MyNat.add_zero
|
||||
|
||||
DefinitionDoc Add as "Add" "`Add a b`, with notation `a + b`, is
|
||||
the usual sum of natural numbers. Internally it is defined by
|
||||
induction on one of the variables, but that is an implementation issue;
|
||||
All you need to know is that `add_zero` and `zero_add` are both theorems."
|
||||
|
||||
NewDefinition Add
|
||||
|
||||
Conclusion
|
||||
"
|
||||
The simplifier atempts to solve goals by using *repeated rewriting* of
|
||||
*equalities* and *iff statements*, and then trying `rfl` at the end.
|
||||
|
||||
Let's now learn about Peano's second axiom for addition, `add_succ`.
|
||||
"
|
||||
47
Game/Levels/Tutorial/L06add_succ.lean
Normal file
47
Game/Levels/Tutorial/L06add_succ.lean
Normal file
@@ -0,0 +1,47 @@
|
||||
import Game.Metadata
|
||||
import Game.MyNat.Addition
|
||||
|
||||
|
||||
World "Tutorial"
|
||||
Level 6
|
||||
Title "add_succ"
|
||||
|
||||
open MyNat
|
||||
|
||||
Introduction
|
||||
"
|
||||
Peano's second axiom was this:
|
||||
|
||||
* `add_succ : ∀ (a b : ℕ), a + succ b = succ (a + b)`
|
||||
|
||||
It tells you that you can move a `succ` left over an `+`. See if you can rewrite
|
||||
your way to a proof of this.
|
||||
"
|
||||
namespace MyNat
|
||||
|
||||
LemmaDoc MyNat.add_succ as "add_succ" in "Add"
|
||||
"`add_succ a b` is the proof of `a + succ b = succ (a + b)`."
|
||||
|
||||
Statement
|
||||
"For all natural numbers $a$, we have $a + \\operatorname{succ}(0) = \\operatorname{succ}(a)$."
|
||||
: a + succ 0 = succ a := by
|
||||
Hint "You find `{a} + succ …` in the goal, so you can use `rw` and `add_succ`
|
||||
to make progress."
|
||||
Hint (hidden := true) "Explicitely, type `rw [add_succ]`!"
|
||||
rw [add_succ]
|
||||
Hint "Now you see a term of the form `… + 0`, so you can use `add_zero`."
|
||||
Hint (hidden := true) "Explicitely, type `rw [add_zero]`!"
|
||||
rw [add_zero]
|
||||
Hint (hidden := true) "Finally both sides are identical."
|
||||
rfl
|
||||
|
||||
Conclusion
|
||||
"
|
||||
You have finished tutorial world! If you're happy, let's move onto Addition World,
|
||||
and learn about proof by induction.
|
||||
|
||||
## Inspection time
|
||||
|
||||
If you want to examine your proofs, toggle \"Editor mode\" and click somewhere
|
||||
inside the proof to see the state of Lean's brain at that point.
|
||||
"
|
||||
@@ -1,100 +0,0 @@
|
||||
import Game.Metadata
|
||||
import Game.MyNat.Addition
|
||||
|
||||
|
||||
World "Tutorial"
|
||||
Level 4
|
||||
Title "addition"
|
||||
|
||||
open MyNat
|
||||
|
||||
Introduction
|
||||
"
|
||||
Peano defined addition $a + b$ by adding two axioms to his system.
|
||||
Peano's first axiom was called `add_zero`. Here it is:
|
||||
|
||||
* `add_zero : ∀ (a : ℕ), a + 0 = a`
|
||||
|
||||
An axiom is just a theorem with a secret proof. The *statement* of the theorem
|
||||
is `∀ (a : ℕ), a + 0 = a`, and the *proof* is `add_zero`. You can't unfold
|
||||
`add_zero` any more: it's an axiom. In Lean, every provable theorem has
|
||||
*exactly one proof*, and it's an \"atom\", just like if $G$ is a group
|
||||
then the elements of $G$ are atoms. The set theory provers (Mizar, Metamath etc)
|
||||
tell us that those atoms, if you look closely enough, are themselves sets.
|
||||
Let me coin a phrase for the simple type theorists such as Isabelle/HOL
|
||||
and he dependent type theorists such as Coq and Lean: let me call them the \"lower type theorists\".
|
||||
Whether or are dependent or simple depends on how seriously you care about category theory; it
|
||||
is not a coincidence that Hales' proof of Kepler had no category theory in it at all.
|
||||
|
||||
The *lower type theorist* a term which I coin to mean the both the simple type theorists
|
||||
such as Isabelle/HOL and the dependent type theorists such as Coq and Lean
|
||||
that is, the simple type theorist ()
|
||||
simply doesn't care.
|
||||
|
||||
|
||||
induction on $b$, or, more precisely, by *recursion* on $b$.
|
||||
In other words, he introduced two axiomsHe first explained how to add $0$ to a number: this is the base case.
|
||||
|
||||
|
||||
We will call this theorem `add_zero`.
|
||||
More precisely, `add_zero` is the name of the *proof* of the
|
||||
theorem. Note the name of this proof. Mathematicians sometimes call it
|
||||
\"Lemma 2.1\" or \"Hypothesis P6\" or something.
|
||||
But computer scientists call it `add_zero` because it tells you what the answer to
|
||||
\"x add zero\" is. It's a much better name than \"Lemma 2.1\".
|
||||
Even better, you can use the `rw` tactic
|
||||
with `add_zero`. If you ever see `x + 0` in your goal,
|
||||
`rw [add_zero]` should simplify it to `x`. This is
|
||||
because `add_zero` is a proof that `x + 0 = x`
|
||||
(more precisely, `add_zero x` is a proof that `x + 0 = x` but
|
||||
Lean can figure out the `x` from the context).
|
||||
|
||||
Now here's the inductive step. If you know how to add $d$ to $a$, then Peano
|
||||
tells you how to add $\\operatorname{succ} (d)$ to $a$. It looks like this:
|
||||
|
||||
- `add_succ (a d : ℕ) : a + (succ d) = succ (a + d)`
|
||||
|
||||
What's going on here is that we assume `a + d` is already defined, and we define
|
||||
`a + (succ d)` to be the number after it.
|
||||
Note the name of this proof too: `add_succ` tells you how to add a successor
|
||||
to something.
|
||||
If you ever see `… + succ …` in your goal, you should be able to use
|
||||
`rw [add_succ]` to make progress.
|
||||
"
|
||||
|
||||
LemmaDoc MyNat.add_succ as "add_succ" in "Add"
|
||||
"One of the two axioms defining addition. It says `n + (succ m) = succ (n + m)`."
|
||||
|
||||
LemmaDoc MyNat.add_zero as "add_zero" in "Add"
|
||||
"One of the two axioms defining addition. It says `n + 0 = n`."
|
||||
|
||||
Statement
|
||||
"For all natural numbers $a$, we have $a + \\operatorname{succ}(0) = \\operatorname{succ}(a)$."
|
||||
: a + succ 0 = succ a := by
|
||||
Hint "You find `{a} + succ …` in the goal, so you can use `rw` and `add_succ`
|
||||
to make progress."
|
||||
Hint (hidden := true) "Explicitely, type `rw [add_succ]`!"
|
||||
rw [add_succ]
|
||||
Hint "Now you see a term of the form `… + 0`, so you can use `add_zero`."
|
||||
Hint (hidden := true) "Explicitely, type `rw [add_zero]`!"
|
||||
Branch
|
||||
simp? -- TODO
|
||||
rw [MyNat.add_zero]
|
||||
Hint (hidden := true) "Finally both sides are identical."
|
||||
rfl
|
||||
|
||||
NewLemma MyNat.add_succ MyNat.add_zero
|
||||
NewDefinition Add
|
||||
|
||||
#check add_zero
|
||||
|
||||
Conclusion
|
||||
"
|
||||
You have finished tutorial world! If you're happy, let's move onto Addition World,
|
||||
and learn about proof by induction.
|
||||
|
||||
## Inspection time
|
||||
|
||||
If you want to examine the proof, toggle \"Editor mode\" and click somewhere
|
||||
inside the proof to see the state at that point!
|
||||
"
|
||||
@@ -1,57 +0,0 @@
|
||||
import Game.Metadata
|
||||
import Game.MyNat.Addition
|
||||
|
||||
|
||||
World "Tutorial"
|
||||
Level 5
|
||||
Title "add_zero"
|
||||
|
||||
open MyNat
|
||||
|
||||
Introduction
|
||||
"
|
||||
`add_zero` is a *proof*, and it is also a *function* at the same time.
|
||||
|
||||
`add_zero` is a proof of `∀ x, x + 0 = x`. In other words, it's a function
|
||||
which eats a number `x` and spits out a proof that the two numbers `x + 0` and `x` are *equal*.
|
||||
|
||||
`rw` is a *tactic* which eats a list of equality proofs and then changes the goal.
|
||||
|
||||
Given the goal below, clearly the way to prove it is just to cancel out all the zeros.
|
||||
So try * `rw [add_zero x]`.
|
||||
"
|
||||
|
||||
LemmaDoc MyNat.add_succ as "add_succ" in "Add"
|
||||
"One of the two axioms defining addition. It says `n + (succ m) = succ (n + m)`."
|
||||
|
||||
LemmaDoc MyNat.add_zero as "add_zero" in "Add"
|
||||
"One of the two axioms defining addition. It says `n + 0 = n`."
|
||||
|
||||
Statement
|
||||
"For all natural numbers $a$, we have $a + \\operatorname{succ}(0) = \\operatorname{succ}(a)$."
|
||||
: a + succ 0 = succ a := by
|
||||
Hint "You find `{a} + succ …` in the goal, so you can use `rw` and `add_succ`
|
||||
to make progress."
|
||||
Hint (hidden := true) "Explicitely, type `rw [add_succ]`!"
|
||||
rw [add_succ]
|
||||
Hint "Now you see a term of the form `… + 0`, so you can use `add_zero`."
|
||||
Hint (hidden := true) "Explicitely, type `rw [add_zero]`!"
|
||||
Branch
|
||||
simp? -- TODO
|
||||
rw [add_zero]
|
||||
Hint (hidden := true) "Finally both sides are identical."
|
||||
rfl
|
||||
|
||||
NewLemma MyNat.add_succ MyNat.add_zero
|
||||
NewDefinition Add
|
||||
|
||||
Conclusion
|
||||
"
|
||||
You have finished tutorial world! If you're happy, let's move onto Addition World,
|
||||
and learn about proof by induction.
|
||||
|
||||
## Inspection time
|
||||
|
||||
If you want to examine the proof, toggle \"Editor mode\" and click somewhere
|
||||
inside the proof to see the state at that point!
|
||||
"
|
||||
@@ -5,16 +5,19 @@ namespace MyNat
|
||||
open MyNat
|
||||
|
||||
def add : MyNat → MyNat → MyNat
|
||||
| a, 0 => a
|
||||
| a, zero => a
|
||||
| a, MyNat.succ b => MyNat.succ (MyNat.add a b)
|
||||
|
||||
instance : Add MyNat where
|
||||
instance instAdd : Add MyNat where
|
||||
add := MyNat.add
|
||||
|
||||
/--
|
||||
This theorem proves that if you add zero to a MyNat you get back the same number.
|
||||
`add_zero a` is a proof of `a + 0 = a`.
|
||||
|
||||
`add_zero` is a `simp` lemma, because if you see `a + 0`
|
||||
you usually want to simplify it to `a`.
|
||||
-/
|
||||
theorem add_zero (a : MyNat) : a + 0 = a := by rfl
|
||||
@[simp] theorem add_zero (a : MyNat) : a + 0 = a := by rfl
|
||||
|
||||
/--
|
||||
This theorem proves that (a + (d + 1)) = ((a + d) + 1) for a,d in MyNat.
|
||||
|
||||
@@ -7,6 +7,6 @@ example (a b : ℕ) (h : (succ a) = b) : succ (succ a) = succ b := by
|
||||
simp
|
||||
sorry
|
||||
|
||||
axiom succ_inj {a b : ℕ} : succ a = succ b → a = b
|
||||
--axiom succ_inj {a b : ℕ} : succ a = succ b → a = b
|
||||
|
||||
axiom zero_ne_succ (a : ℕ) : 0 ≠ succ a
|
||||
--axiom zero_ne_succ (a : ℕ) : 0 ≠ succ a
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import Game.Levels.Tutorial.L02rw-- makes simps work?
|
||||
import Game.MyNat.Addition-- makes simps work?
|
||||
import Mathlib.Tactic
|
||||
namespace MyNat
|
||||
|
||||
@@ -51,7 +51,7 @@ We need to learn how to deal wiht a goal of the form `P → Q`
|
||||
|
||||
-/
|
||||
|
||||
theorem succ_inj (a b : ℕ) (h : succ a = succ b) : a = b := by
|
||||
theorem succ_inj {a b : ℕ} (h : succ a = succ b) : a = b := by
|
||||
apply_fun pred at h
|
||||
simpa
|
||||
|
||||
@@ -90,7 +90,7 @@ congrArg pred
|
||||
-/
|
||||
@[simp] theorem succ_eq_succ_iff : succ a = succ b ↔ a = b := by
|
||||
constructor
|
||||
· exact succ_inj a b
|
||||
· exact succ_inj
|
||||
· simp
|
||||
|
||||
/-
|
||||
|
||||
Reference in New Issue
Block a user