lean4-htt/tests/lean/derivingDecidableEq.lean
Joachim Breitner b5555052bd
feat: T.ctor.elim single-constructor cases function (#9952)
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.
2025-08-27 09:40:31 +00:00

30 lines
619 B
Text
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

structure Fin' (n : Nat) where
val : Nat
isLt : val < n
deriving DecidableEq
#eval
(Fin'.mk 0 (Nat.lt.step (Nat.lt.base 0)): Fin' 2)
= (Fin'.mk 0 (Nat.lt.step (Nat.lt.base 0)) : Fin' 2)
#eval
(Fin'.mk 0 (Nat.lt.step (Nat.lt.base 0)): Fin' 2)
= (Fin'.mk 1 (Nat.lt.base 1) : Fin' 2)
inductive List' (α : Type u) where
| nil : List' α
| cons (head : α) (tail : List' α) (h : head = head) : List' α
deriving DecidableEq
#eval
List'.nil.cons 0 rfl
= List'.nil.cons 0 rfl
#eval
List'.nil.cons 0 rfl
= (List'.nil.cons 0 rfl).cons 1 rfl
structure A
deriving DecidableEq
#eval A.mk = A.mk