Skip to content

Commit f8d88ed

Browse files
committed
feat: optimized simp routine for let telescopes
This PR adds the following features to `simp`: - A routine for simplifying `let` telescopes, like what #6220 did for `letFun` telescopes. Furthermore, simp converts `letFun`s into `have`s (nondependent lets), and we remove the #6220 routine. - A `+letToHave` configuration option (enabled by default) that converts lets into haves when possible, when `-zeta` is set. Previosuly Lean would need to do a full typecheck the bodies of `let`s, but the `letToHave` procedure can be faster, and it modifies the `let`s in an entire expression at once. - A `+zetaHave` configuration option, to turn off zeta reduction of `have`s specifically. The motivation is that dependent `let`s can only be dsimped by let, so zeta reducing just nondependent lets is a reasonable way to make progress.
1 parent a427a82 commit f8d88ed

File tree

10 files changed

+1021
-240
lines changed

10 files changed

+1021
-240
lines changed

src/Init/MetaTypes.lean

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,6 @@ structure Config where
123123
-/
124124
zetaUnused : Bool := true
125125
/--
126-
(Unimplemented)
127126
When `false` (default: `true`), then disables zeta reduction of `have` expressions.
128127
If `zeta` is `false`, then this option has no effect.
129128
Unused `have`s are still removed if `zeta` or `zetaUnused` are true.
@@ -261,14 +260,12 @@ structure Config where
261260
-/
262261
catchRuntime : Bool := true
263262
/--
264-
(Unimplemented)
265263
When `false` (default: `true`), then disables zeta reduction of `have` expressions.
266264
If `zeta` is `false`, then this option has no effect.
267265
Unused `have`s are still removed if `zeta` or `zetaUnused` are true.
268266
-/
269267
zetaHave : Bool := true
270268
/--
271-
(Unimplemented)
272269
When `true` (default : `true`), then `simp` will attempt to transform `let`s into `have`s
273270
if they are non-dependent. This only applies when `zeta := false`.
274271
-/

src/Lean/Elab/PreDefinition/WF/Preprocess.lean

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -176,6 +176,8 @@ private def nonPropHaveToLet (e : Expr) : MetaM Expr := do
176176
def preprocess (e : Expr) : MetaM Simp.Result := do
177177
unless wf.preprocess.get (← getOptions) do
178178
return { expr := e }
179+
-- Transform `let`s to `have`s to enable `simp` entering let bodies.
180+
let e ← letToHave e
179181
lambdaTelescope e fun xs _ => do
180182
-- Annotate all xs with `wfParam`
181183
let xs' ← xs.mapM mkWfParam

src/Lean/Meta/Tactic/Simp/Main.lean

Lines changed: 334 additions & 195 deletions
Large diffs are not rendered by default.

tests/lean/convPatternAtLetIssue.lean

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ def f (x : Nat) := x
33
def test : (λ x => f x)
44
=
55
(λ x : Nat =>
6-
let foo := λ y => id (id y)
6+
have foo := λ y => id (id y)
77
foo x) := by
88
conv =>
99
pattern (id _)

tests/lean/run/3943.lean

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ example (f : Nat → Nat) : f x = 0 → f x + 1 = y := by
88
guard_target =ₛ f x = 01 = y
99
sorry
1010

11-
example (f : Nat → Nat) : let _ : f x = 0 := sorryAx _ false; f x + 1 = y := by
11+
example (f : Nat → Nat) : have _ : f x = 0 := sorryAx _ false; f x + 1 = y := by
1212
simp (config := { contextual := true, zeta := false, zetaUnused := false })
1313
guard_target =ₛ have _ : f x = 0 := sorryAx _ false; 1 = y
1414
sorry
@@ -45,7 +45,7 @@ example : (if p x then g x else g x + 1) + g x = y := by
4545
guard_target =ₛ (if p x then x else g x + 1) + g x = y
4646
sorry
4747

48-
example : (let _ : p x := sorryAx _ false; g x + 1 = y) ↔ g x = y := by
48+
example : (have _ : p x := sorryAx _ false; g x + 1 = y) ↔ g x = y := by
4949
simp (config := { zeta := false, zetaUnused := false }) (discharger := assumption)
5050
guard_target =ₛ (have _ : p x := sorryAx _ false; x + 1 = y) ↔ g x = y
5151
sorry

0 commit comments

Comments
 (0)