l3lab/ntp-mathlib huggingface dataset:
theorem ListBlank.nth_modifyNth {Γ} [Inhabited Γ] (f : Γ → Γ) (n i) (L : ListBlank Γ) :
    (L.modifyNth f n).nth i = if i = n then f (L.nth i) else L.nth i := by
  induction' n with n IH generalizing i L
  · 

Proof state:
case zero
Γ : Type u_1
inst✝ : Inhabited Γ
f : Γ → Γ
i : ℕ
L : ListBlank Γ
⊢ nth (modifyNth f Nat.zero L) i = if i = Nat.zero then f (nth L i) else nth L i

Next tactic:
cases i
theorem ListBlank.nth_modifyNth {Γ} [Inhabited Γ] (f : Γ → Γ) (n i) (L : ListBlank Γ) :
    (L.modifyNth f n).nth i = if i = n then f (L.nth i) else L.nth i := by
  induction' n with n IH generalizing i L
  · cases i <;> 

Proof state:
case zero.zero
Γ : Type u_1
inst✝ : Inhabited Γ
f : Γ → Γ
L : ListBlank Γ
⊢ nth (modifyNth f Nat.zero L) Nat.zero = if Nat.zero = Nat.zero then f (nth L Nat.zero) else nth L Nat.zero

Next tactic:
simp only [ListBlank.nth_zero, if_true, ListBlank.head_cons, ListBlank.modifyNth,
      ListBlank.nth_succ, if_false, ListBlank.tail_cons, Nat.zero_eq]
theorem ListBlank.nth_modifyNth {Γ} [Inhabited Γ] (f : Γ → Γ) (n i) (L : ListBlank Γ) :
    (L.modifyNth f n).nth i = if i = n then f (L.nth i) else L.nth i := by
  induction' n with n IH generalizing i L
  · cases i <;> 

Proof state:
case zero.succ
Γ : Type u_1
inst✝ : Inhabited Γ
f : Γ → Γ
L : ListBlank Γ
n✝ : ℕ
⊢ nth (modifyNth f Nat.zero L) (Nat.succ n✝) =
    if Nat.succ n✝ = Nat.zero then f (nth L (Nat.succ n✝)) else nth L (Nat.succ n✝)

Next tactic:
simp only [ListBlank.nth_zero, if_true, ListBlank.head_cons, ListBlank.modifyNth,
      ListBlank.nth_succ, if_false, ListBlank.tail_cons, Nat.zero_eq]
theorem ListBlank.nth_modifyNth {Γ} [Inhabited Γ] (f : Γ → Γ) (n i) (L : ListBlank Γ) :
    (L.modifyNth f n).nth i = if i = n then f (L.nth i) else L.nth i := by
  induction' n with n IH generalizing i L
  · cases i <;> simp only [ListBlank.nth_zero, if_true, ListBlank.head_cons, ListBlank.modifyNth,
      ListBlank.nth_succ, if_false, ListBlank.tail_cons, Nat.zero_eq]
  · 

Proof state:
case succ
Γ : Type u_1
inst✝ : Inhabited Γ
f : Γ → Γ
n : ℕ
IH : ∀ (i : ℕ) (L : ListBlank Γ), nth (modifyNth f n L) i = if i = n then f (nth L i) else nth L i
i : ℕ
L : ListBlank Γ
⊢ nth (modifyNth f (Nat.succ n) L) i = if i = Nat.succ n then f (nth L i) else nth L i

Next tactic:
cases i
theorem ListBlank.nth_modifyNth {Γ} [Inhabited Γ] (f : Γ → Γ) (n i) (L : ListBlank Γ) :
    (L.modifyNth f n).nth i = if i = n then f (L.nth i) else L.nth i := by
  induction' n with n IH generalizing i L
  · cases i <;> simp only [ListBlank.nth_zero, if_true, ListBlank.head_cons, ListBlank.modifyNth,
      ListBlank.nth_succ, if_false, ListBlank.tail_cons, Nat.zero_eq]
  · cases i
    · 

Proof state:
case succ.zero
Γ : Type u_1
inst✝ : Inhabited Γ
f : Γ → Γ
n : ℕ
IH : ∀ (i : ℕ) (L : ListBlank Γ), nth (modifyNth f n L) i = if i = n then f (nth L i) else nth L i
L : ListBlank Γ
⊢ nth (modifyNth f (Nat.succ n) L) Nat.zero = if Nat.zero = Nat.succ n then f (nth L Nat.zero) else nth L Nat.zero

Next tactic:
rw [if_neg (Nat.succ_ne_zero _).symm]
theorem ListBlank.nth_modifyNth {Γ} [Inhabited Γ] (f : Γ → Γ) (n i) (L : ListBlank Γ) :
    (L.modifyNth f n).nth i = if i = n then f (L.nth i) else L.nth i := by
  induction' n with n IH generalizing i L
  · cases i <;> simp only [ListBlank.nth_zero, if_true, ListBlank.head_cons, ListBlank.modifyNth,
      ListBlank.nth_succ, if_false, ListBlank.tail_cons, Nat.zero_eq]
  · cases i
    · rw [if_neg (Nat.succ_ne_zero _).symm]
      

Proof state:
case succ.zero
Γ : Type u_1
inst✝ : Inhabited Γ
f : Γ → Γ
n : ℕ
IH : ∀ (i : ℕ) (L : ListBlank Γ), nth (modifyNth f n L) i = if i = n then f (nth L i) else nth L i
L : ListBlank Γ
⊢ nth (modifyNth f (Nat.succ n) L) Nat.zero = nth L Nat.zero

Next tactic:
simp only [ListBlank.nth_zero, ListBlank.head_cons, ListBlank.modifyNth, Nat.zero_eq]
theorem ListBlank.nth_modifyNth {Γ} [Inhabited Γ] (f : Γ → Γ) (n i) (L : ListBlank Γ) :
    (L.modifyNth f n).nth i = if i = n then f (L.nth i) else L.nth i := by
  induction' n with n IH generalizing i L
  · cases i <;> simp only [ListBlank.nth_zero, if_true, ListBlank.head_cons, ListBlank.modifyNth,
      ListBlank.nth_succ, if_false, ListBlank.tail_cons, Nat.zero_eq]
  · cases i
    · rw [if_neg (Nat.succ_ne_zero _).symm]
      simp only [ListBlank.nth_zero, ListBlank.head_cons, ListBlank.modifyNth, Nat.zero_eq]
    · 

Proof state:
case succ.succ
Γ : Type u_1
inst✝ : Inhabited Γ
f : Γ → Γ
n : ℕ
IH : ∀ (i : ℕ) (L : ListBlank Γ), nth (modifyNth f n L) i = if i = n then f (nth L i) else nth L i
L : ListBlank Γ
n✝ : ℕ
⊢ nth (modifyNth f (Nat.succ n) L) (Nat.succ n✝) =
    if Nat.succ n✝ = Nat.succ n then f (nth L (Nat.succ n✝)) else nth L (Nat.succ n✝)

Next tactic:
simp only [IH, ListBlank.modifyNth, ListBlank.nth_succ, ListBlank.tail_cons, Nat.succ.injEq]
@[simp]
theorem PointedMap.headI_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : List Γ) : (l.map f).headI = f l.headI := by
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : List Γ
⊢ List.headI (List.map f.f l) = Turing.PointedMap.f f (List.headI l)

Next tactic:
cases l <;> [exact (PointedMap.map_pt f).symm; rfl]
@[simp]
theorem PointedMap.headI_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : List Γ) : (l.map f).headI = f l.headI := by
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : List Γ
⊢ List.headI (List.map f.f l) = Turing.PointedMap.f f (List.headI l)

Next tactic:
cases l
@[simp]
theorem PointedMap.headI_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : List Γ) : (l.map f).headI = f l.headI := by
  cases l <;> [

Proof state:
case nil
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
⊢ List.headI (List.map f.f []) = Turing.PointedMap.f f (List.headI [])

Next tactic:
exact (PointedMap.map_pt f).symm
@[simp]
theorem PointedMap.headI_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : List Γ) : (l.map f).headI = f l.headI := by
  cases l <;> [exact (PointedMap.map_pt f).symm; 

Proof state:
case cons
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
head✝ : Γ
tail✝ : List Γ
⊢ List.headI (List.map f.f (head✝ :: tail✝)) = Turing.PointedMap.f f (List.headI (head✝ :: tail✝))

Next tactic:
rfl
/-- The `map` function on lists is well defined on `ListBlank`s provided that the map is
pointed. -/
def ListBlank.map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ') (l : ListBlank Γ) :
    ListBlank Γ' := by
  

Proof state:
Γ : Type ?u.29098
Γ' : Type ?u.29097
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
⊢ ListBlank Γ'

Next tactic:
apply l.liftOn (fun l ↦ ListBlank.mk (List.map f l))
/-- The `map` function on lists is well defined on `ListBlank`s provided that the map is
pointed. -/
def ListBlank.map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ') (l : ListBlank Γ) :
    ListBlank Γ' := by
  apply l.liftOn (fun l ↦ ListBlank.mk (List.map f l))
  

Proof state:
Γ : Type ?u.29098
Γ' : Type ?u.29097
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
⊢ ∀ (a b : List Γ), BlankExtends a b → mk (List.map f.f a) = mk (List.map f.f b)

Next tactic:
rintro l _ ⟨i, rfl⟩
/-- The `map` function on lists is well defined on `ListBlank`s provided that the map is
pointed. -/
def ListBlank.map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ') (l : ListBlank Γ) :
    ListBlank Γ' := by
  apply l.liftOn (fun l ↦ ListBlank.mk (List.map f l))
  rintro l _ ⟨i, rfl⟩; 

Proof state:
case intro
Γ : Type ?u.29098
Γ' : Type ?u.29097
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
l : List Γ
i : ℕ
⊢ mk (List.map f.f l) = mk (List.map f.f (l ++ List.replicate i default))

Next tactic:
refine' Quotient.sound' (Or.inl ⟨i, _⟩)
/-- The `map` function on lists is well defined on `ListBlank`s provided that the map is
pointed. -/
def ListBlank.map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ') (l : ListBlank Γ) :
    ListBlank Γ' := by
  apply l.liftOn (fun l ↦ ListBlank.mk (List.map f l))
  rintro l _ ⟨i, rfl⟩; refine' Quotient.sound' (Or.inl ⟨i, _⟩)
  

Proof state:
case intro
Γ : Type ?u.29098
Γ' : Type ?u.29097
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
l : List Γ
i : ℕ
⊢ List.map f.f (l ++ List.replicate i default) = List.map f.f l ++ List.replicate i default

Next tactic:
simp only [PointedMap.map_pt, List.map_append, List.map_replicate]
@[simp]
theorem ListBlank.head_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).head = f l.head := by
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
⊢ head (map f l) = PointedMap.f f (head l)

Next tactic:
conv => lhs; rw [← ListBlank.cons_head_tail l]
@[simp]
theorem ListBlank.head_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).head = f l.head := by
  conv => 

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
| head (map f l) = PointedMap.f f (head l)

Next tactic:
lhs; rw [← ListBlank.cons_head_tail l]
@[simp]
theorem ListBlank.head_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).head = f l.head := by
  conv => 

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
| head (map f l) = PointedMap.f f (head l)

Next tactic:
lhs
@[simp]
theorem ListBlank.head_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).head = f l.head := by
  conv => lhs; 

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
| head (map f l)

Next tactic:
rw [← ListBlank.cons_head_tail l]
@[simp]
theorem ListBlank.head_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).head = f l.head := by
  conv => lhs; rw [← ListBlank.cons_head_tail l]
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
⊢ head (map f (cons (head l) (tail l))) = PointedMap.f f (head l)

Next tactic:
exact Quotient.inductionOn' l fun a ↦ rfl
@[simp]
theorem ListBlank.tail_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).tail = l.tail.map f := by
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
⊢ tail (map f l) = map f (tail l)

Next tactic:
conv => lhs; rw [← ListBlank.cons_head_tail l]
@[simp]
theorem ListBlank.tail_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).tail = l.tail.map f := by
  conv => 

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
| tail (map f l) = map f (tail l)

Next tactic:
lhs; rw [← ListBlank.cons_head_tail l]
@[simp]
theorem ListBlank.tail_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).tail = l.tail.map f := by
  conv => 

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
| tail (map f l) = map f (tail l)

Next tactic:
lhs
@[simp]
theorem ListBlank.tail_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).tail = l.tail.map f := by
  conv => lhs; 

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
| tail (map f l)

Next tactic:
rw [← ListBlank.cons_head_tail l]
@[simp]
theorem ListBlank.tail_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) : (l.map f).tail = l.tail.map f := by
  conv => lhs; rw [← ListBlank.cons_head_tail l]
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
⊢ tail (map f (cons (head l) (tail l))) = map f (tail l)

Next tactic:
exact Quotient.inductionOn' l fun a ↦ rfl
@[simp]
theorem ListBlank.map_cons {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (a : Γ) : (l.cons a).map f = (l.map f).cons (f a) := by
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
a : Γ
⊢ map f (cons a l) = cons (PointedMap.f f a) (map f l)

Next tactic:
refine' (ListBlank.cons_head_tail _).symm.trans _
@[simp]
theorem ListBlank.map_cons {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (a : Γ) : (l.cons a).map f = (l.map f).cons (f a) := by
  refine' (ListBlank.cons_head_tail _).symm.trans _
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
a : Γ
⊢ cons (head (map f (cons a l))) (tail (map f (cons a l))) = cons (PointedMap.f f a) (map f l)

Next tactic:
simp only [ListBlank.head_map, ListBlank.head_cons, ListBlank.tail_map, ListBlank.tail_cons]
@[simp]
theorem ListBlank.nth_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (n : ℕ) : (l.map f).nth n = f (l.nth n) := by
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l : ListBlank Γ
n : ℕ
⊢ nth (map f l) n = PointedMap.f f (nth l n)

Next tactic:
refine' l.inductionOn fun l ↦ _
@[simp]
theorem ListBlank.nth_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (n : ℕ) : (l.map f).nth n = f (l.nth n) := by
  refine' l.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
n : ℕ
l : List Γ
⊢ nth (map f ⟦l⟧) n = PointedMap.f f (nth ⟦l⟧ n)

Next tactic:
suffices ((mk l).map f).nth n = f ((mk l).nth n) by exact this
@[simp]
theorem ListBlank.nth_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (n : ℕ) : (l.map f).nth n = f (l.nth n) := by
  refine' l.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  suffices ((mk l).map f).nth n = f ((mk l).nth n) by 

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
n : ℕ
l : List Γ
this : nth (map f (mk l)) n = PointedMap.f f (nth (mk l) n)
⊢ nth (map f ⟦l⟧) n = PointedMap.f f (nth ⟦l⟧ n)

Next tactic:
exact this
@[simp]
theorem ListBlank.nth_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (n : ℕ) : (l.map f).nth n = f (l.nth n) := by
  refine' l.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  suffices ((mk l).map f).nth n = f ((mk l).nth n) by exact this
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
n : ℕ
l : List Γ
⊢ nth (map f (mk l)) n = PointedMap.f f (nth (mk l) n)

Next tactic:
simp only [List.get?_map, ListBlank.map_mk, ListBlank.nth_mk, List.getI_eq_iget_get?]
@[simp]
theorem ListBlank.nth_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (n : ℕ) : (l.map f).nth n = f (l.nth n) := by
  refine' l.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  suffices ((mk l).map f).nth n = f ((mk l).nth n) by exact this
  simp only [List.get?_map, ListBlank.map_mk, ListBlank.nth_mk, List.getI_eq_iget_get?]
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
n : ℕ
l : List Γ
⊢ Option.iget (Option.map f.f (List.get? l n)) = PointedMap.f f (Option.iget (List.get? l n))

Next tactic:
cases l.get? n
@[simp]
theorem ListBlank.nth_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (n : ℕ) : (l.map f).nth n = f (l.nth n) := by
  refine' l.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  suffices ((mk l).map f).nth n = f ((mk l).nth n) by exact this
  simp only [List.get?_map, ListBlank.map_mk, ListBlank.nth_mk, List.getI_eq_iget_get?]
  cases l.get? n
  · 

Proof state:
case none
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
n : ℕ
l : List Γ
⊢ Option.iget (Option.map f.f none) = PointedMap.f f (Option.iget none)

Next tactic:
exact f.2.symm
@[simp]
theorem ListBlank.nth_map {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (f : PointedMap Γ Γ')
    (l : ListBlank Γ) (n : ℕ) : (l.map f).nth n = f (l.nth n) := by
  refine' l.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  suffices ((mk l).map f).nth n = f ((mk l).nth n) by exact this
  simp only [List.get?_map, ListBlank.map_mk, ListBlank.nth_mk, List.getI_eq_iget_get?]
  cases l.get? n
  · exact f.2.symm
  · 

Proof state:
case some
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
f : PointedMap Γ Γ'
l✝ : ListBlank Γ
n : ℕ
l : List Γ
val✝ : Γ
⊢ Option.iget (Option.map f.f (some val✝)) = PointedMap.f f (Option.iget (some val✝))

Next tactic:
rfl
theorem proj_map_nth {ι : Type*} {Γ : ι → Type*} [∀ i, Inhabited (Γ i)] (i : ι) (L n) :
    (ListBlank.map (@proj ι Γ _ i) L).nth n = L.nth n i := by
  

Proof state:
ι : Type u_1
Γ : ι → Type u_2
inst✝ : (i : ι) → Inhabited (Γ i)
i : ι
L : ListBlank ((i : ι) → Γ i)
n : ℕ
⊢ ListBlank.nth (ListBlank.map (proj i) L) n = ListBlank.nth L n i

Next tactic:
rw [ListBlank.nth_map]
theorem proj_map_nth {ι : Type*} {Γ : ι → Type*} [∀ i, Inhabited (Γ i)] (i : ι) (L n) :
    (ListBlank.map (@proj ι Γ _ i) L).nth n = L.nth n i := by
  rw [ListBlank.nth_map]; 

Proof state:
ι : Type u_1
Γ : ι → Type u_2
inst✝ : (i : ι) → Inhabited (Γ i)
i : ι
L : ListBlank ((i : ι) → Γ i)
n : ℕ
⊢ PointedMap.f (proj i) (ListBlank.nth L n) = ListBlank.nth L n i

Next tactic:
rfl
theorem ListBlank.map_modifyNth {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (F : PointedMap Γ Γ')
    (f : Γ → Γ) (f' : Γ' → Γ') (H : ∀ x, F (f x) = f' (F x)) (n) (L : ListBlank Γ) :
    (L.modifyNth f n).map F = (L.map F).modifyNth f' n := by
  

Proof state:
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
F : PointedMap Γ Γ'
f : Γ → Γ
f' : Γ' → Γ'
H : ∀ (x : Γ), PointedMap.f F (f x) = f' (PointedMap.f F x)
n : ℕ
L : ListBlank Γ
⊢ map F (modifyNth f n L) = modifyNth f' n (map F L)

Next tactic:
induction' n with n IH generalizing L
theorem ListBlank.map_modifyNth {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (F : PointedMap Γ Γ')
    (f : Γ → Γ) (f' : Γ' → Γ') (H : ∀ x, F (f x) = f' (F x)) (n) (L : ListBlank Γ) :
    (L.modifyNth f n).map F = (L.map F).modifyNth f' n := by
  induction' n with n IH generalizing L <;>
    

Proof state:
case zero
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
F : PointedMap Γ Γ'
f : Γ → Γ
f' : Γ' → Γ'
H : ∀ (x : Γ), PointedMap.f F (f x) = f' (PointedMap.f F x)
L : ListBlank Γ
⊢ map F (modifyNth f Nat.zero L) = modifyNth f' Nat.zero (map F L)

Next tactic:
simp only [*, ListBlank.head_map, ListBlank.modifyNth, ListBlank.map_cons, ListBlank.tail_map]
theorem ListBlank.map_modifyNth {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (F : PointedMap Γ Γ')
    (f : Γ → Γ) (f' : Γ' → Γ') (H : ∀ x, F (f x) = f' (F x)) (n) (L : ListBlank Γ) :
    (L.modifyNth f n).map F = (L.map F).modifyNth f' n := by
  induction' n with n IH generalizing L <;>
    

Proof state:
case succ
Γ : Type u_1
Γ' : Type u_2
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
F : PointedMap Γ Γ'
f : Γ → Γ
f' : Γ' → Γ'
H : ∀ (x : Γ), PointedMap.f F (f x) = f' (PointedMap.f F x)
n : ℕ
IH : ∀ (L : ListBlank Γ), map F (modifyNth f n L) = modifyNth f' n (map F L)
L : ListBlank Γ
⊢ map F (modifyNth f (Nat.succ n) L) = modifyNth f' (Nat.succ n) (map F L)

Next tactic:
simp only [*, ListBlank.head_map, ListBlank.modifyNth, ListBlank.map_cons, ListBlank.tail_map]
@[simp]
theorem ListBlank.append_mk {Γ} [Inhabited Γ] (l₁ l₂ : List Γ) :
    ListBlank.append l₁ (ListBlank.mk l₂) = ListBlank.mk (l₁ ++ l₂) := by
  

Proof state:
Γ : Type u_1
inst✝ : Inhabited Γ
l₁ l₂ : List Γ
⊢ append l₁ (mk l₂) = mk (l₁ ++ l₂)

Next tactic:
induction l₁
@[simp]
theorem ListBlank.append_mk {Γ} [Inhabited Γ] (l₁ l₂ : List Γ) :
    ListBlank.append l₁ (ListBlank.mk l₂) = ListBlank.mk (l₁ ++ l₂) := by
  induction l₁ <;>
    

Proof state:
case nil
Γ : Type u_1
inst✝ : Inhabited Γ
l₂ : List Γ
⊢ append [] (mk l₂) = mk ([] ++ l₂)

Next tactic:
simp only [*, ListBlank.append, List.nil_append, List.cons_append, ListBlank.cons_mk]
@[simp]
theorem ListBlank.append_mk {Γ} [Inhabited Γ] (l₁ l₂ : List Γ) :
    ListBlank.append l₁ (ListBlank.mk l₂) = ListBlank.mk (l₁ ++ l₂) := by
  induction l₁ <;>
    

Proof state:
case cons
Γ : Type u_1
inst✝ : Inhabited Γ
l₂ : List Γ
head✝ : Γ
tail✝ : List Γ
tail_ih✝ : append tail✝ (mk l₂) = mk (tail✝ ++ l₂)
⊢ append (head✝ :: tail✝) (mk l₂) = mk (head✝ :: tail✝ ++ l₂)

Next tactic:
simp only [*, ListBlank.append, List.nil_append, List.cons_append, ListBlank.cons_mk]
theorem ListBlank.append_assoc {Γ} [Inhabited Γ] (l₁ l₂ : List Γ) (l₃ : ListBlank Γ) :
    ListBlank.append (l₁ ++ l₂) l₃ = ListBlank.append l₁ (ListBlank.append l₂ l₃) := by
  

Proof state:
Γ : Type u_1
inst✝ : Inhabited Γ
l₁ l₂ : List Γ
l₃ : ListBlank Γ
⊢ append (l₁ ++ l₂) l₃ = append l₁ (append l₂ l₃)

Next tactic:
refine' l₃.inductionOn fun l ↦ _
theorem ListBlank.append_assoc {Γ} [Inhabited Γ] (l₁ l₂ : List Γ) (l₃ : ListBlank Γ) :
    ListBlank.append (l₁ ++ l₂) l₃ = ListBlank.append l₁ (ListBlank.append l₂ l₃) := by
  refine' l₃.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  

Proof state:
Γ : Type u_1
inst✝ : Inhabited Γ
l₁ l₂ : List Γ
l₃ : ListBlank Γ
l : List Γ
⊢ append (l₁ ++ l₂) ⟦l⟧ = append l₁ (append l₂ ⟦l⟧)

Next tactic:
suffices append (l₁ ++ l₂) (mk l) = append l₁ (append l₂ (mk l)) by exact this
theorem ListBlank.append_assoc {Γ} [Inhabited Γ] (l₁ l₂ : List Γ) (l₃ : ListBlank Γ) :
    ListBlank.append (l₁ ++ l₂) l₃ = ListBlank.append l₁ (ListBlank.append l₂ l₃) := by
  refine' l₃.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  suffices append (l₁ ++ l₂) (mk l) = append l₁ (append l₂ (mk l)) by 

Proof state:
Γ : Type u_1
inst✝ : Inhabited Γ
l₁ l₂ : List Γ
l₃ : ListBlank Γ
l : List Γ
this : append (l₁ ++ l₂) (mk l) = append l₁ (append l₂ (mk l))
⊢ append (l₁ ++ l₂) ⟦l⟧ = append l₁ (append l₂ ⟦l⟧)

Next tactic:
exact this
theorem ListBlank.append_assoc {Γ} [Inhabited Γ] (l₁ l₂ : List Γ) (l₃ : ListBlank Γ) :
    ListBlank.append (l₁ ++ l₂) l₃ = ListBlank.append l₁ (ListBlank.append l₂ l₃) := by
  refine' l₃.inductionOn fun l ↦ _
  -- Porting note: Added `suffices` to get `simp` to work.
  suffices append (l₁ ++ l₂) (mk l) = append l₁ (append l₂ (mk l)) by exact this
  

Proof state:
Γ : Type u_1
inst✝ : Inhabited Γ
l₁ l₂ : List Γ
l₃ : ListBlank Γ
l : List Γ
⊢ append (l₁ ++ l₂) (mk l) = append l₁ (append l₂ (mk l))

Next tactic:
simp only [ListBlank.append_mk, List.append_assoc]
/-- The `bind` function on lists is well defined on `ListBlank`s provided that the default element
is sent to a sequence of default elements. -/
def ListBlank.bind {Γ Γ'} [Inhabited Γ] [Inhabited Γ'] (l : ListBlank Γ) (f : Γ → List Γ')
    (hf : ∃ n, f default = List.replicate n default) : ListBlank Γ' := by
  

Proof state:
Γ : Type ?u.37228
Γ' : Type ?u.37240
inst✝¹ : Inhabited Γ
inst✝ : Inhabited Γ'
l : ListBlank Γ
f : Γ → List Γ'
hf : ∃ n, f default = List.replicate n default
⊢ ListBlank Γ'

Next tactic:
apply l.liftOn (fun l ↦ ListBlank.mk (List.bind l f))