blob: 8724eb46a1967c1db2e914fe25e825d0d40f6e3e [file] [edit]
def Vec (α : Type u) (n : Nat) : Type u := { a : List α // a.length = n }
def Vec.nil : Vec α 0 := ⟨[], rfl⟩
def Vec.cons (a : α) (as : Vec α n) : Vec α (n+1) := ⟨a :: as.val, by simp [as.property]⟩
set_option pp.analyze false
set_option linter.unusedVariables false
set_option pp.mvars false
def Vec.casesOn
(motive : (n : Nat) → Vec α n → Sort v)
(n : Nat)
(as : Vec α n)
(nil : motive 0 Vec.nil)
(cons : (n : Nat) → (a : α) → (as : Vec α n) → (ih : motive n as) → motive (n+1) (Vec.cons a as))
: motive n as :=
let rec go (n : Nat) (as : List α) (h : as.length = n) : motive n ⟨as, h⟩ :=
match n, as, h with
| 0, [], _ => nil
| n+1, a::as, h =>
have : as.length = n := by injection h
have ih : motive n ⟨as, this⟩ := go n as this
cons n a ⟨as, this⟩ ih
match as with
| ⟨as, h⟩ => go n as h
/--
trace: α : Type u_1
n✝ : Nat
a✝ : α
as✝ : Vec α n✝
x✝ n : Nat
a : α
as : Vec α n
ih : as = as
⊢ Vec.cons a as = Vec.cons a as
-/
#guard_msgs in
example (n : Nat) (a : α) (as : Vec α n) : Vec.cons a (Vec.cons a as) = Vec.cons a (Vec.cons a as) := by
induction n+2, Vec.cons a (Vec.cons a as) using Vec.casesOn
case nil => constructor
case cons n a as ih =>
trace_state
constructor
/--
trace: α : Type u_1
n✝ : Nat
a✝ : α
as✝ : Vec α n✝
n : Nat
a : α
as : Vec α n
ih : n + 1 = n → Vec.cons a as ≍ as → Vec.cons a as = Vec.cons a as
⊢ Vec.cons a as = Vec.cons a as
-/
#guard_msgs in
example (n : Nat) (a : α) (as : Vec α n) : Vec.cons a (Vec.cons a as) = Vec.cons a (Vec.cons a as) := by
cases n+2, Vec.cons a (Vec.cons a as) using Vec.casesOn
case nil => constructor
case cons n a as ih =>
trace_state
constructor
/--
trace: α : Type u_1
n : Nat
a : α
as : Vec α n
n' : Nat
a' : α
as' : Vec α n'
h₁ : n + 2 = n' + 1
h₂ : Vec.cons a (Vec.cons a as) ≍ Vec.cons a' as'
ih : n' + 1 = n' → Vec.cons a' as' ≍ as' → Vec.cons a' as' = Vec.cons a' as'
⊢ Vec.cons a' as' = Vec.cons a' as'
-/
#guard_msgs in
example (n : Nat) (a : α) (as : Vec α n) : Vec.cons a (Vec.cons a as) = Vec.cons a (Vec.cons a as) := by
cases h₁ : n+2, h₂ : Vec.cons a (Vec.cons a as) using Vec.casesOn
case nil => constructor
case cons n' a' as' ih =>
trace_state
constructor