lean4-htt/tests/lean/run/4320.lean
Joachim Breitner f0a11b8864
fix: FunInd: support structural recursion on reflexive types (#4327)
types like
```
inductive Many (α : Type u) where
  | none : Many α
  | more : α → (Unit → Many α) → Many α
```
have a `.brecOn` only supports motives producing `Type u`, but not `Sort
u`, but our induction principles produce `Prop`. So the previous
implementation of functional induction would fail for functions that
structurally recurse over such types.

We recognize this case now and, rather hazardously, replace `.brecOn`
with `.binductionOn` (and thus `.below ` with `.ibelow` and `PProd` with
`And`). This assumes that these definitions are highly analogous.

This also improves the error message when realizing a reserved name
fails with an exception, by prepending
```
Failed to realize constant {id}:
```
to the error message.

Fixes #4320
2024-06-05 07:54:48 +00:00

23 lines
858 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.

inductive Many (α : Type u) where
| none : Many α
| more : α → (Unit → Many α) → Many α
def many_map {α β : Type} (f : α → β) : Many α → Many β
| .none => .none
| .more x xs => Many.more (f x) (fun () => many_map f <| xs ())
/--
info: many_map.induct {α β : Type} (f : α → β) (motive : Many α → Prop) (case1 : motive Many.none)
(case2 : ∀ (x : α) (xs : Unit → Many α), motive (xs ()) → motive (Many.more x xs)) : ∀ (a : Many α), motive a
-/
#guard_msgs in
#check many_map.induct
-- Unrelated, but for fun, show that we get the identical theorem from well-founded recursion
def many_map' {α β : Type} (f : α → β) : Many α → Many β
| .none => .none
| .more x xs => Many.more (f x) (fun () => many_map' f <| xs ())
termination_by m => m
example : @many_map.induct = @many_map'.induct := rfl