feat: implementation of @[use_set_notation]#37347
feat: implementation of @[use_set_notation]#37347JovanGerb wants to merge 1 commit intoleanprover-community:masterfrom
@[use_set_notation]#37347Conversation
PR summary e885514426Import changes for modified filesNo significant changes to the import graph Import changes for all files
|
There was a problem hiding this comment.
This looks great! :) My comments here are mostly administrative or minor; the content of the metaprogramming looks solid. I've gone through carefully and ensured all names and syntax precedences line up, and everything checks out. :)
Also, could you please copy-paste most of the PR description from #32983 into this PR? I think it would be helpful to have it available in the git blame for this file.
|
|
||
| /-- Delaborate `x ≤ y` into `x ⊆ y` if the type is tagged with `@[use_set_notation]`. -/ | ||
| @[app_delab LE.le] | ||
| def delabLe : Delab := whenNotPPOption getPPExplicit <| whenPPOption getPPNotation do |
There was a problem hiding this comment.
We should probably namespace these under some appropriate SetNotation-related namespace, but see the file-level suggestion on naming.
| let x ← withNaryArg 2 delab | ||
| let y ← withNaryArg 3 delab | ||
| let stx ← `($x ⊆ $y) | ||
| annotateGoToDef stx `Mathlib.Meta.delabLe |
There was a problem hiding this comment.
(Here and below, to make this stable under refactors)
| annotateGoToDef stx `Mathlib.Meta.delabLe | |
| annotateGoToDef stx decl_name% |
|
|
||
| /-! ## Elaboration -/ | ||
|
|
||
| /-- This relation is an implementation detail of the `⊆` elatorator. -/ |
There was a problem hiding this comment.
Typo:
| /-- This relation is an implementation detail of the `⊆` elatorator. -/ | |
| /-- This relation is an implementation detail of the `⊆` elaborator. -/ |
| /-- Elaborate a notation like `a ⊆ b` by elaborating `a` and `b`, and then deciding | ||
| based on their type whether to return `a ⊆ b` or `a ≤ b`. | ||
| Use `a ≤ b` whenever `useSetNotationFor` returns true for the type. | ||
| If the type is not known, elaboration of this term is postponed. -/ |
There was a problem hiding this comment.
| If the type is not known, elaboration of this term is postponed. -/ | |
| If the type is not known, elaboration of this term is postponed. | |
| We assume that `le` and `sub` are names for declarations of exactly the form | |
| `decl.{u} {α : Type u} [Cls.{u} α] (a b : α) : Prop`, and that likewise `leCls` and `subCls` are | |
| names for declarations of exactly the form `Cls.{u} (α : Type u) : Type u`. -/ |
There was a problem hiding this comment.
What do you think about calling this file SetlikeOrderNotation, and renaming the definitions in it accordingly? E.g. @[setlike_order_notation].
I know there are plans to expand this functionality; do they all have to do with using setlike notation for order-related operations, or do some have to do with {}, {|}, complementation, and ∈? That's the ambiguity in the phrase "set notation" I'm trying to eliminate here; SetNotation is by itself a bit broad!
There was a problem hiding this comment.
That sound good to me, indeed it seems that all set notations involved are about order. (Note that for complements, we already use the same constant for sets and boolean algebras)
| if ← useSetNotationFor α then | ||
| let inst ← mkInstMVar <| .app (.const leCls f.constLevels!) α | ||
| return mkApp4 (.const le f.constLevels!) α inst x y | ||
| else | ||
| let inst ← mkInstMVar <| .app (.const subCls f.constLevels!) α | ||
| return mkApp4 (.const sub f.constLevels!) α inst x y |
There was a problem hiding this comment.
Note: I wonder if it's worth adding hover info to the subset token specifically to show which relation it wound up elaborating to. 🤔 However, command-clicking brings up the instances, so I think this is likely fine as-is, and my experiments in adding hover info to the token actually interfere with that command-clicking on the broader term. Let me know if you have thoughts here, though.
|
|
||
| /-- Elaborator for `x ⊂ y` notation. -/ | ||
| @[term_elab ssubsetStx'] | ||
| def elabSsubsetStx' : TermElab |
There was a problem hiding this comment.
(Following HasSSubset)
| def elabSsubsetStx' : TermElab | |
| def elabSSubsetStx' : TermElab |
|
|
||
| /-- Elaborator for `x ⊃ y` notation. -/ | ||
| @[term_elab ssupsetStx'] | ||
| def elabSsupsetStx' : TermElab |
There was a problem hiding this comment.
(Following HasSSubset)
| def elabSsupsetStx' : TermElab | |
| def elabSSupsetStx' : TermElab |
There was a problem hiding this comment.
Could you please
- Move this file out of Delab, and name it analogously to the source file it's testing
- Include tests for the elaborating/delaborating the other 3 relations? It's alright if they're minimal (or combined in a single statement!), I just want to make sure we test them since I anticipate they won't be used very much (and so it might not be obvious if they break).
|
|
||
| /-- Whether to use set notation for the given type or not. -/ | ||
| def useSetNotationFor (type : Expr) : MetaM Bool := do | ||
| let .const n _ := (← whnfR type).getAppFn | return false |
There was a problem hiding this comment.
I think this is probably appropriate, especially given that we might use it after synthesizeSyntheticMVars* later on:
| let .const n _ := (← whnfR type).getAppFn | return false | |
| let .const n _ := (← whnfR <| ← instantiateMVars type).getAppFn | return false |
|
Here's a half-thought re: the |
|
Note that these issues arise in Another solution would be to default to |
This PR is the implementation part of #32983, without using the feature yet.