Zulip Chat Archive
Stream: lean4
Topic: CPDT in lean
Remi (Jan 04 2022 at 00:42):
Hi, I currently rewriting code from CPDT and stuck with stack machine semantic proof.
I have several questions about lean:
- How can I make non-opaque alias for type.
- Is there any tactic for automatic proofs like sauto.
There's also a problem with actual proof.
p : List Instr
s : List Nat
bop : BinOp
e₁ e₂ : Expr
ih₁ : programDenote (compile e₁ ++ p) s = programDenote p (exprDenote e₁ :: s) [Click to join video call](https://meet.jit.si/185444530925654)
ih₂ : programDenote (compile e₂ ++ p) s = programDenote p (exprDenote e₂ :: s)
⊢ programDenote (compile e₂ ++ (compile e₁ ++ ([iBinOp bop] ++ p))) s =
programDenote p (binOpDenote bop (exprDenote e₁) (exprDenote e₂) :: s)
In this proof context lean doesn't want to rewrite with ih₂, but this expression obviously has an appropriate type and works fine with simple rewrite tactic in coq.
There's a link to full code
Chris B (Jan 04 2022 at 01:02):
There's no hammer equivalent in Lean4. You can make a non-opaque alias with either abbrev <name> := ..
or @[reducible] def <name> := ..
.
Chris B (Jan 04 2022 at 01:04):
w.r.t. sauto
, There's library_search
, but it's not as beefy as other proof search stuff.
Joe Hendrix (Jan 04 2022 at 01:06):
@Remi I'd expect ih_1
and ih_2
to have the form Forall (p:List Instr)
, if they had that form, then simp or rewrite should likely work.
Reid Barton (Jan 04 2022 at 01:12):
Right, ih₂
is about some specific program p
, but the goal is about some different program built from p
, so ih₂
doesn't apply.
Reid Barton (Jan 04 2022 at 01:12):
A bit hard to guess without context, but maybe you want to generalize p
before doing an induction.
Chris B (Jan 04 2022 at 01:13):
theorem compileCorrect' e (p:List Instr) (s:List Nat) : programDenote (compile e ++ p) s = programDenote p (exprDenote e :: s) := by
induction e generalizing p with
| const => rfl
| binOp bop e₁ e₂ ih₁ ih₂ =>
simp [compile]
simp [exprDenote]
rw [List.append_assoc]
rw [List.append_assoc]
generalize hx : (compile e₁ ++ ([iBinOp bop] ++ p)) = p'
rw [ih₂] -- succeeds now.
sorry
Reid Barton (Jan 04 2022 at 01:15):
ah whoops, I missed that there was a link to the code!
Remi (Jan 04 2022 at 01:17):
@Chris B Can you explain what differs your code from mine?
Chris B (Jan 04 2022 at 01:17):
The generalizing
bit in induction e generalizing p
.
Chris B (Jan 04 2022 at 01:18):
It changes the inductive hypotheses.
Remi (Jan 04 2022 at 01:18):
Oh, now I understand.
Thank's everyone for the help!
Chris B (Jan 04 2022 at 01:20):
@Remi btw stuff to the right of the colon gets generalized automatically, some people find that more intuitive. This achieves the same result:
theorem compileCorrect' e : ∀ (p:List Instr) (s:List Nat), programDenote (compile e ++ p) s = programDenote p (exprDenote e :: s) := by
induction e with
Remi (Jan 04 2022 at 02:39):
There's full proof :smile: .
theorem compileCorrect' (e:Expr) (p:List Instr) (s:List Nat) : programDenote (compile e ++ p) s = programDenote p (exprDenote e :: s) := by
induction e generalizing p s with
| const => rfl
| binOp bop e₁ e₂ ih₁ ih₂ =>
simp [compile, exprDenote]
rw [List.append_assoc, List.append_assoc]
rw [ih₂, ih₁]
simp [programDenote, instrDenote]
rfl
done
Chris B (Jan 04 2022 at 03:19):
Way to go. By the way, where did you see that syntax for addressing the induction cases with .
instead of | constructor .. =>
?
Remi (Jan 04 2022 at 03:37):
@Chris B https://leanprover.github.io/theorem_proving_in_lean4/tactics.html#basic-tactics
Last updated: Dec 20 2023 at 11:08 UTC