Conversation
rish987
added a commit
to rish987/lean4
that referenced
this pull request
Sep 14, 2026
This PR speeds up kernel typechecking by reusing free variable names across lambda and forall binders that share the same domain type, so that subterms recurring under different binders become structurally identical instead of differing only in a fresh variable name. This lets the kernel's definitional-equality cache reuse previously computed results far more often, including nontrivial facts about terms that are merely defeq rather than syntactically equal. On a full Mathlib replay the kernel is about 16% faster, with no change in which declarations are accepted. When entering a binder of domain type `D`, the type checker now reuses a free variable name previously generated for `D` (picking the lowest index not currently in scope) rather than always generating a fresh one. Because a reused free variable consistently denotes a variable of type `D`, this is a consistent renaming of free variables that preserves definitional equality, and the in-scope check guarantees it never conflates two distinct variables. The checker state maps each domain type to a reusable name prefix; `let` binders keep using fresh names. Ported from the lean4lean fvar-reuse optimization (digama0/lean4lean#5). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QpT8QtSD8fb2RL9r59eXKx
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This PR adds an optimization to the typechecker implementation to make better use of the
EquivManagerdefinitional equality cache by reusing free variables where possible.As a motivating example, suppose we have defeq terms
TandScontaining free variablex, and we callisDefEqonfun (a : A) (b : B) => T[x := a]andfun (a : A) (b : B) => S[x := a]. This will cache the equality betweenT[x := f1]andS[x := f2], wheref1andf2are new free variables generated upon entering the lambda binders foraandb.However, if we later call
isDefEqonfun (b : B) (a : A) => T[x := a]andfun (b : B) (a : A) => S[x := a], we will check the cache forT[x := f3]andS[x := f4], using the newly generated fvarsf3andf4, resulting in a miss. Ideally, we would want to have reusedf1andf2here so that we could take advantage of the cached knowledge thatT[x := f1]andS[x := f2]are defeq.When entering into a forall or lambda binder of domain type
D, it should be sound to reuse an fvar that was previously generated forDin a different context (as long asDhas not already been bound in the current context). Any fvars appearing inDwould also have to be reused fvars that were generated for previously seen domain types, and so on for the fvars in their types.I've implemented this by replacing the
NameGeneratorin the typechecker state with a simple counter, and using a hashmap from domain type expressions to previously generated fvar names that is checked whenever a new fvar name needs to be generated upon entering a lambda or forall binder. With this optimization, Mathlib typechecks about 20% faster when Lean4Lean is run sequentially.