levels
This commit is contained in:
@@ -0,0 +1,42 @@
|
||||
import TestGame.Metadata
|
||||
|
||||
import Mathlib
|
||||
|
||||
set_option tactic.hygienic false
|
||||
|
||||
Game "TestGame"
|
||||
World "LeanStuff"
|
||||
Level 1
|
||||
|
||||
Title "Typen"
|
||||
|
||||
Introduction
|
||||
"
|
||||
Dieses Kapitel führt ein paar Lean-spezifische Sachen ein, die du wissen solltest.
|
||||
|
||||
Mathematisch haben diese Sachen keinen Inhalt, aber es ist wichtig, dass du etwas
|
||||
verstehst wie Lean manche Sachen macht.
|
||||
|
||||
Als erstes geht es um Typen.
|
||||
|
||||
Oft sieht man Argumente von der Form `(U : Type)` was heisst \"sei $U$ ein Typ.\"
|
||||
Als Mathematiker kann man sich Typen ein bisschen wie Mengen vorstellen, in dem Sinn
|
||||
dass sie die Grundlage der Mathematik bilden: Alles sind Typen.
|
||||
|
||||
Zum Beispiel ist `ℕ` der Typ der natürlichen Zahlen, `Prop` der Typ der logischen
|
||||
Aussagen, und ein Ring ist ein Typ `(R : Type)` zusammen mit einer Instanz `[Ring R]`,
|
||||
die sagt, dass auf diesem Typ eine Ringstruktur besteht.
|
||||
|
||||
**Achtung**: Wie du aber gleich sehen wirst sind Typen und Mengen in Lean komplett
|
||||
unterschiedliche Sachen! (Und Mengen nehmen in Lean nicht die fundamentale Funktion
|
||||
ein, die sie in der Mathe innehaben.)
|
||||
"
|
||||
|
||||
Statement
|
||||
""
|
||||
(R : Type) [CommRing R] (a b : R) : a + b = b + a := by
|
||||
ring
|
||||
|
||||
Hint (R : Type) (h : CommRing R) (a : R) (b : R) : a + b = b + a =>
|
||||
"Die Taktik `ring` funktioniert in jedem Typen,
|
||||
der mindestens eine Instanz `[Ring R]` hat."
|
||||
@@ -17,10 +17,36 @@ Dieses Kapitel führt ein paar Lean-spezifische Sachen ein, die du wissen sollte
|
||||
Mathematisch haben diese Sachen keinen Inhalt, aber es ist wichtig, dass du etwas
|
||||
verstehst wie Lean manche Sachen macht.
|
||||
|
||||
Als erstes geht es um implizite und explizite Argumente von Lemmas. **Explizite Argumente**
|
||||
schreibt man mit runden Klammern `()`, **impliziete Argumente** mit geschweiften `{}`.
|
||||
|
||||
- Implizite und explizite Argumente.
|
||||
- Types
|
||||
Als implizit werden alle Argumente markiert, die Lean selbständig aus dem Kontext
|
||||
erschliessen und einfüllen kann.
|
||||
|
||||
Als Beispiel hier zweimal das gleiche Lemma, einmal ohne impliziten Argumenten und einmal mit
|
||||
```
|
||||
lemma not_or_of_imp' (A B : Prop) (h : A → B) : ¬A ∨ B := sorry
|
||||
|
||||
lemma not_or_of_imp {A B : Prop} (h : A → B) : ¬A ∨ B := sorry
|
||||
```
|
||||
|
||||
Hat man nun `g : C → D` dann braucht man diese Lemmas mit
|
||||
`have := not_or_of_imp g` oder `have := not_or_of_imp' C D g`.
|
||||
|
||||
Wie man sieht erschliesst Lean die impliziten Argumente automatisch und es wäre deshalb
|
||||
unnötig, diese jedes Mal explizit angeben zu müssen.
|
||||
|
||||
TODO
|
||||
(Trick mit `@not_or_of_imp` kann man sagen, dass man **alle** Argumente angeben möchte und mir
|
||||
`not_or_of_imp g (B := D)` könnte man ein spezifisches implizites Argument spezifizieren.
|
||||
Wenn man diese Tricks braucht, heisst das aber meistens, das etwas nicht optimal definiert
|
||||
ist.)
|
||||
|
||||
TODO
|
||||
Zudem gibt es noch Argumente in eckigen Klammern `[]`. Dies sind auch implizite
|
||||
Argumente, die aber von der **Instance Resolution** gefüllt werden sollen. Dies
|
||||
wird später kommen, aber ein typisches Beispiel ist `(S : Type _) [ring S]` was Lean
|
||||
sagt, es soll suchen gehen, ob es weiss, dass `S` ein Ring ist.
|
||||
"
|
||||
|
||||
open Set
|
||||
@@ -30,3 +56,6 @@ Statement
|
||||
trivial
|
||||
|
||||
NewTactics rw
|
||||
|
||||
#check not_not
|
||||
#check not_or_of_imp
|
||||
|
||||
@@ -0,0 +1,37 @@
|
||||
import TestGame.Metadata
|
||||
|
||||
import Mathlib
|
||||
|
||||
set_option tactic.hygienic false
|
||||
|
||||
Game "TestGame"
|
||||
World "LeanStuff"
|
||||
Level 2
|
||||
|
||||
Title "Universen"
|
||||
|
||||
Introduction
|
||||
"
|
||||
In der Mathematik stösst man manchmal an Mengentheoretische Grenzen, und so auch in Lean.
|
||||
|
||||
Klassisch ist bekannt dass die \"Menge aller Mengen\" nicht existieren kann.
|
||||
|
||||
Falls man an diese Grenzen stösst (z.B. in der Mengenlehre oder Kategorientheorie) hat Lean
|
||||
Universen bereit: `Type` ist eigentlich `Type 0` und es gibt auch `Type 1, Type 2, ...`
|
||||
|
||||
Deshalb sieht man oft in Lean-Code `(R : Type _)` wenn es keine mengentheoretischen
|
||||
Probleme gibt (`_` ist ein Platzhalter) oder `universe u` am Anfang und dann `(R : Type u)`
|
||||
falls man diese mengentheoretischen Probleme kontrollieren muss.
|
||||
|
||||
In der Praxis kommt man aber relativ weit, wenn man sich erst mal nicht mit Universen
|
||||
beschäftigt, und lediglich weiss, dass es sowas gibt.
|
||||
"
|
||||
|
||||
Statement
|
||||
"TODO"
|
||||
(R S : Type _) [CommRing R] (a b : R) : a + b = b + a := by
|
||||
ring
|
||||
|
||||
Hint (R : Type _) (h : CommRing R) (a : R) (b : R) : a + b = b + a =>
|
||||
"Die Taktik `ring` funktioniert in jedem Typen,
|
||||
der mindestens eine Instanz `[Ring R]` hat."
|
||||
@@ -0,0 +1,57 @@
|
||||
import TestGame.Metadata
|
||||
|
||||
import Mathlib
|
||||
|
||||
set_option tactic.hygienic false
|
||||
|
||||
Game "TestGame"
|
||||
World "LeanStuff"
|
||||
Level 3
|
||||
|
||||
Title "Implizite Argumente"
|
||||
|
||||
Introduction
|
||||
"
|
||||
|
||||
Auch wichtiger Syntax ist der Unterschied zwischen
|
||||
impliziten und expliziten Argumenten von Lemmas. **Explizite Argumente**
|
||||
schreibt man mit runden Klammern `()`, **impliziete Argumente** mit geschweiften `{}`.
|
||||
|
||||
Als implizit werden alle Argumente markiert, die Lean selbständig aus dem Kontext
|
||||
erschliessen und einfüllen kann.
|
||||
|
||||
Als Beispiel hier zweimal das gleiche Lemma, einmal ohne impliziten Argumenten und einmal mit
|
||||
```
|
||||
lemma not_or_of_imp' (A B : Prop) (h : A → B) : ¬A ∨ B := sorry
|
||||
|
||||
lemma not_or_of_imp {A B : Prop} (h : A → B) : ¬A ∨ B := sorry
|
||||
```
|
||||
|
||||
Hat man nun `g : C → D` dann braucht man diese Lemmas mit
|
||||
`have := not_or_of_imp g` oder `have := not_or_of_imp' C D g`.
|
||||
|
||||
Wie man sieht erschliesst Lean die impliziten Argumente automatisch und es wäre deshalb
|
||||
unnötig, diese jedes Mal explizit angeben zu müssen.
|
||||
|
||||
TODO
|
||||
(Trick mit `@not_or_of_imp` kann man sagen, dass man **alle** Argumente angeben möchte und mir
|
||||
`not_or_of_imp g (B := D)` könnte man ein spezifisches implizites Argument spezifizieren.
|
||||
Wenn man diese Tricks braucht, heisst das aber meistens, das etwas nicht optimal definiert
|
||||
ist.)
|
||||
|
||||
|
||||
Nebenbemerkung: Es gibt auch noch implizite **Klassen-Elemente** mit eckigen Klammern `[]`
|
||||
wie zum Beispiel `[CommRing R]` im vorigen Beispiel. Diese werden später behandelt,
|
||||
und sagen Lean, dass es für dieses Argument eine **Instanz** suchen gehen soll. Diese
|
||||
Instanzen werden mehrheitlich dafür verwendet, mathematische Strukturen auf Typen zu
|
||||
definieren, aber das kommt alles später.
|
||||
"
|
||||
|
||||
Statement
|
||||
"TODO"
|
||||
(R S : Type _) [CommRing R] (a b : R) : a + b = b + a := by
|
||||
ring
|
||||
|
||||
Hint (R : Type _) (h : CommRing R) (a : R) (b : R) : a + b = b + a =>
|
||||
"Die Taktik `ring` funktioniert in jedem Typen,
|
||||
der mindestens eine Instanz `[Ring R]` hat."
|
||||
Reference in New Issue
Block a user