Theorem: List.list_reverse_induction
File: Mathlib/Data/List/Indexes.lean

Proof steps:
state_before: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
⊢ ∀ (l : List α), p l
state_after: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
⊢ ∀ (l : List α), p l
tactic: let q := fun l ↦ p (reverse l)
state_before: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
⊢ ∀ (l : List α), p l
state_after: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
⊢ ∀ (l : List α), p l
tactic: have pq : ∀ l, p (reverse l) → q l := by simp only [q, reverse_reverse]; intro; exact id
state_before: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
⊢ ∀ (l : List α), p l
state_after: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
⊢ ∀ (l : List α), p l
tactic: have qp : ∀ l, q (reverse l) → p l := by simp only [q, reverse_reverse]; intro; exact id
state_before: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
⊢ ∀ (l : List α), p l
state_after: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l : List α
⊢ p l
tactic: intro l
state_before: α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l : List α
⊢ p l
state_after: case a
α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l : List α
⊢ q l.reverse
tactic: apply qp
state_before: case a
α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l : List α
⊢ q l.reverse
state_after: case a
α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l✝ l : List α
⊢ q l
tactic: generalize (reverse l) = l
state_before: case a
α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l✝ l : List α
⊢ q l
state_after: case a.nil
α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l : List α
⊢ q []

case a.cons
α : Type u
β : Type v
p : List α → Prop
base : p []
ind : ∀ (l : List α) (e : α), p l → p (l ++ [e])
q : List α → Prop := fun l => p l.reverse
pq : ∀ (l : List α), p l.reverse → q l
qp : ∀ (l : List α), q l.reverse → p l
l : List α
head : α
tail : List α
ih : q tail
⊢ q (head :: tail)
tactic: induction' l with head tail ih