This PR removes some `grind` annotations for `Array.attach` and related
functions. These lemmas introduce lambda on the right hand side which
`grind` can't do much with. I've added a test file that verifies that
the theorems with removed annotations can actually be proved already by
grind. Removing the annotations will help with excessive instantiation.
This PR completes the review of `@[grind]` annotations without a sigil
(e.g. `=` or `←`), replacing most of them with more specific annotations
or patterns.
---------
Co-authored-by: Leonardo de Moura <leomoura@amazon.com>
This PR adds “non-branching case statements”: For each inductive
constructor `T.con` this adds a function `T.con.with` that is similar
`T.casesOn`, but has only one arm (the one for `con`), and an additional
`t.toCtorIdx = 12` assumption.
For example:
```lean
inductive Vec (α : Type) : Nat → Type where
| nil : Vec α 0
| cons {n} : α → Vec α n → Vec α (n + 1)
/--
info: @[reducible] protected def Vec.cons.elim.{u} : {α : Type} →
{motive : (a : Nat) → Vec α a → Sort u} →
{a : Nat} →
(t : Vec α a) →
t.ctorIdx = 1 → ({n : Nat} → (a : α) → (a_1 : Vec α n) → motive (n + 1) (Vec.cons a a_1)) → motive a t
-/
#guard_msgs in
#print sig Vec.cons.elim
```
This is a building block for non-quadratic implementations of `BEq` and
`DecidableEq` etc.
Builds on top of #9951.
The compiled code for a these functions could presumably, without
branching on the inductive value, directly access the fields. Achieving
this optimization (and achieving it without a quadratic compilation
cost) is not in scope for this PR.
This PR reviews `grind` annotations for `Option`, preferring to use
`@[grind =]` instead of `@[grind]` (and fixing a few problems revealed
by this), and making sure `@[grind =]` theorems are "fully applied".
This PR tries to improve the E-matching pattern inference for `grind`.
That said, we still need better tools for annotating and maintaining
`grind` annotations in libraries.
closes#9125
This PR moves the construction of the `Option.SomeLtNone.lt` (and `le`)
relation, in which `some` is less than `none`, to
`Init.Data.Option.Basic` and moves well-foundedness proofs for
`Option.lt` and `Option.SomeLtNone.lt` into `Init.Data.Option.Lemmas`.
This PR adjusts the experimental module system to make `private` the
default visibility modifier in `module`s, introducing `public` as a new
modifier instead. `public section` can be used to revert the default for
an entire section, though this is more intended to ease gradual adoption
of the new semantics such as in `Init` (and soon `Std`) where they
should be replaced by a future decl-by-decl re-review of visibilities.
This PR removes the `@[reducible]` annotation on `Array.size`. This is
probably best gone anyway in order to keep separation between the `List`
and `Array` APIs, but it also helps avoid uselessly instantiating
`Array` theorems when `grind` is working on `List` problems.
This PR adds the `@[expose]` attribute to many functions (and changes
some theorems to be by `:= (rfl)`) in preparation for the `@[defeq]`
attribute change in #8419.
This PR adds further `@[grind]` annotations for `Option`, as follow-up
to the recent additions to the `Option` API in #8379 and #8298.
**However**, I am concurrently investigating adding `attribute [grind
cases] Option`, which will result in many (most?) of the annotations for
`Option` being removed again. In any case, I'm going to merge this
first, as if that is viable I would like to test that most/all the
lemmas now marked with `@[grind]` are still provable by `grind`.
This PR reworks the `simp` set around the `Id` monad, to not elide or
unfold `pure` and `Id.run`
In particular, it stops encoding the "defeq abuse" of `Id X = X` in the
statements of theorems, instead using `Id.run` and `pure` to pass back
and forth between these two spellings. Often when writing these with
`pure`, they generalize to other lawful monads; though such changes were
split off to other PRs.
This fixes the problem with the current simp set where `Id.run (pure x)`
is simplified to `Id.run x`, instead of the desirable `x`.
This is particularly bad because the` x` is sometimes inferred with type
`Id X` instead of `X`, which prevents other `simp` lemmas about `X` from
firing.
Making `Id` reducible instead is not an option, as then the `Monad`
instances would have nothing to key on.
---------
Co-authored-by: Sebastian Graf <sg@lean-fro.org>
Co-authored-by: Kim Morrison <kim@tqft.net>
Co-authored-by: Paul Reichert <6992158+datokrat@users.noreply.github.com>
This PR adds missing `Option` lemmas.
Also:
- generalize `bindM` from `Monad` to `Pure`
- change the `simp` normal form of both `<|>` and `Option.orElse` to
`Option.or`
This PR adjusts the experimental module system to not export the bodies
of `def`s unless opted out by the new attribute `@[expose]` on the `def`
or on a surrounding `section`.
---------
Co-authored-by: Markus Himmel <markus@lean-fro.org>
This PR adds unconditional lemmas for
`HashMap.getElem?_insertMany_list`, alongside the existing ones that
have quite strong preconditions. Also for TreeMap (and
dependent/extensional variants).
This PR changes the predicate for `Option.guard` to be `p : α → Bool`
instead of `p : α → Prop`. This brings it in line with other comparable
functions like `Option.filter`.
This PR adds an initial set of `@[grind]` annotations for
`List`/`Array`/`Vector`, enough to set up some regression tests using
`grind` in proofs about `List`. More annotations to follow.
This PR adds lemmas for the `filter`, `map` and `filterMap` functions of
the hash map.
---------
Co-authored-by: jt0202 <johannes.tantow@gmail.com>
Co-authored-by: Johannes Tantow <44068763+jt0202@users.noreply.github.com>
Co-authored-by: Markus Himmel <markus@himmel-villmar.de>
This PR moves `ReflBEq` to `Init.Core` and changes `LawfulBEq` to extend
`ReflBEq`.
**BREAKING CHANGES:**
- The `refl` field of `ReflBEq` has been renamed to `rfl` to match
`LawfulBEq`
- `LawfulBEq` extends `ReflBEq`, so in particular `LawfulBEq.rfl` is no
longer valid
This PR cleans up the `Option` development, upstreaming some results
from mathlib in the process.
Notable changes:
- the name `<op>_eq_some_iff` is preferred over `<op>_eq_some`
- the `simp` normal form for `<$>` is `Option.map`, for `>>=` is
`Option.bind` and for `<|>` is `Option.orElse` (for the former two, this
was already true before this PR). All further lemmas about these
operations are now stated only in terms of
`Option.map`/`Option.bind`/`Option.orElse`. Previously, in some cases
both versions were available, with a prime used to disambiguate (the
primed version was usually the "non-ascii-art" version). Now, there are
no lemmas about the ascii-art versions besides the ones turning them
into the non-ascii-art operations, and there is only one version of
every lemma, about the non-ascii-art operation, and named without a
prime.
This PR generalizes the typeclass assumptions on monadic `Option`
functions.
`Option.mapA` is now an alias for `Option.mapM`, which now works for
applicative functors. The changed definition is exactly equivalent for
monads which use the default implementation of `map`, and those who
change it will hopefully choose a definition for `map` that is more
efficient and not less efficient. `Option.mapA` is not deprecated in
order to keep the API aligned with `List` (`List.mapA` and `List.mapM`
cannot be unified because the monadic version is much more efficient
than the applicative version).
This PR partially reverts #7818, because the function called
`Option.zipWith` in that PR does not actually correspond to
`List.zipWith`. We choose `Option.merge` as the name instead.
This PR changes definitions and theorems not to use the membership
instance on `Option` unless the theorem is specifically about the
membership instance.
The reasoning for this change is that the lemma `a ∈ o ↔ o = some a` is
a `simp` lemma, and we generally want theorem statements to use `simp`
normal forms.
One notable exception is the `ForIn'` instance, which must use
`Membership` because unlike `GetElem`, `ForIn'` requires the validity
predicate to be expressed via `Membership`.
This PR adds `Option.pfilter`, a variant of `Option.filter` and several
lemmas for it and other `Option` functions. These lemmas are split off
from #7400.