l3lab/ntp-mathlib huggingface dataset:
theorem suppPreservation_iff_liftpPreservation : q.SuppPreservation ↔ q.LiftPPreservation := by
  constructor <;> intro h
  · rintro α p ⟨a, f⟩
    have h' := h
    rw [suppPreservation_iff_isUniform] at h'
    dsimp only [SuppPreservation, supp] at h
    simp only [liftP_iff_of_isUniform, supp_eq_of_isUniform, MvPFunctor.liftP_iff', h',
      image_univ, mem_range, exists_imp]
    constructor <;> intros <;> subst_vars <;> 

Proof state:
case mp.mk.mp
n : ℕ
F : TypeVec.{u} n → Type u_1
inst✝ : MvFunctor F
q : MvQPF F
h : ∀ ⦃α : TypeVec.{u} n⦄ (x : ↑(P F) α), supp (abs x) = supp x
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
a : (P F).A
f : MvPFunctor.B (P F) a ⟹ α
h' : IsUniform
a✝ : ∀ (i : Fin2 n) (u : α i) (x : MvPFunctor.B (P F) a i), f i x = u → p u
i✝ : Fin2 n
x✝ : MvPFunctor.B (P F) a i✝
⊢ p (f i✝ x✝)

Next tactic:
solve_by_elim
theorem suppPreservation_iff_liftpPreservation : q.SuppPreservation ↔ q.LiftPPreservation := by
  constructor <;> intro h
  · rintro α p ⟨a, f⟩
    have h' := h
    rw [suppPreservation_iff_isUniform] at h'
    dsimp only [SuppPreservation, supp] at h
    simp only [liftP_iff_of_isUniform, supp_eq_of_isUniform, MvPFunctor.liftP_iff', h',
      image_univ, mem_range, exists_imp]
    constructor <;> intros <;> subst_vars <;> 

Proof state:
case mp.mk.mpr
n : ℕ
F : TypeVec.{u} n → Type u_1
inst✝ : MvFunctor F
q : MvQPF F
h : ∀ ⦃α : TypeVec.{u} n⦄ (x : ↑(P F) α), supp (abs x) = supp x
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
a : (P F).A
f : MvPFunctor.B (P F) a ⟹ α
h' : IsUniform
a✝ : ∀ (i : Fin2 n) (x : MvPFunctor.B (P F) a i), p (f i x)
i✝ : Fin2 n
x✝ : MvPFunctor.B (P F) a i✝
⊢ p (f i✝ x✝)

Next tactic:
solve_by_elim
theorem suppPreservation_iff_liftpPreservation : q.SuppPreservation ↔ q.LiftPPreservation := by
  constructor <;> intro h
  · rintro α p ⟨a, f⟩
    have h' := h
    rw [suppPreservation_iff_isUniform] at h'
    dsimp only [SuppPreservation, supp] at h
    simp only [liftP_iff_of_isUniform, supp_eq_of_isUniform, MvPFunctor.liftP_iff', h',
      image_univ, mem_range, exists_imp]
    constructor <;> intros <;> subst_vars <;> solve_by_elim
  · 

Proof state:
case mpr
n : ℕ
F : TypeVec.{u} n → Type u_1
inst✝ : MvFunctor F
q : MvQPF F
h : LiftPPreservation
⊢ SuppPreservation

Next tactic:
rintro α ⟨a, f⟩
theorem suppPreservation_iff_liftpPreservation : q.SuppPreservation ↔ q.LiftPPreservation := by
  constructor <;> intro h
  · rintro α p ⟨a, f⟩
    have h' := h
    rw [suppPreservation_iff_isUniform] at h'
    dsimp only [SuppPreservation, supp] at h
    simp only [liftP_iff_of_isUniform, supp_eq_of_isUniform, MvPFunctor.liftP_iff', h',
      image_univ, mem_range, exists_imp]
    constructor <;> intros <;> subst_vars <;> solve_by_elim
  · rintro α ⟨a, f⟩
    

Proof state:
case mpr.mk
n : ℕ
F : TypeVec.{u} n → Type u_1
inst✝ : MvFunctor F
q : MvQPF F
h : LiftPPreservation
α : TypeVec.{u} n
a : (P F).A
f : MvPFunctor.B (P F) a ⟹ α
⊢ supp (abs { fst := a, snd := f }) = supp { fst := a, snd := f }

Next tactic:
simp only [LiftPPreservation] at h
theorem suppPreservation_iff_liftpPreservation : q.SuppPreservation ↔ q.LiftPPreservation := by
  constructor <;> intro h
  · rintro α p ⟨a, f⟩
    have h' := h
    rw [suppPreservation_iff_isUniform] at h'
    dsimp only [SuppPreservation, supp] at h
    simp only [liftP_iff_of_isUniform, supp_eq_of_isUniform, MvPFunctor.liftP_iff', h',
      image_univ, mem_range, exists_imp]
    constructor <;> intros <;> subst_vars <;> solve_by_elim
  · rintro α ⟨a, f⟩
    simp only [LiftPPreservation] at h
    

Proof state:
case mpr.mk
n : ℕ
F : TypeVec.{u} n → Type u_1
inst✝ : MvFunctor F
q : MvQPF F
h : ∀ ⦃α : TypeVec.{u} n⦄ (p : ⦃i : Fin2 n⦄ → α i → Prop) (x : ↑(P F) α), LiftP p (abs x) ↔ LiftP p x
α : TypeVec.{u} n
a : (P F).A
f : MvPFunctor.B (P F) a ⟹ α
⊢ supp (abs { fst := a, snd := f }) = supp { fst := a, snd := f }

Next tactic:
ext
theorem suppPreservation_iff_liftpPreservation : q.SuppPreservation ↔ q.LiftPPreservation := by
  constructor <;> intro h
  · rintro α p ⟨a, f⟩
    have h' := h
    rw [suppPreservation_iff_isUniform] at h'
    dsimp only [SuppPreservation, supp] at h
    simp only [liftP_iff_of_isUniform, supp_eq_of_isUniform, MvPFunctor.liftP_iff', h',
      image_univ, mem_range, exists_imp]
    constructor <;> intros <;> subst_vars <;> solve_by_elim
  · rintro α ⟨a, f⟩
    simp only [LiftPPreservation] at h
    ext
    

Proof state:
case mpr.mk.h.h
n : ℕ
F : TypeVec.{u} n → Type u_1
inst✝ : MvFunctor F
q : MvQPF F
h : ∀ ⦃α : TypeVec.{u} n⦄ (p : ⦃i : Fin2 n⦄ → α i → Prop) (x : ↑(P F) α), LiftP p (abs x) ↔ LiftP p x
α : TypeVec.{u} n
a : (P F).A
f : MvPFunctor.B (P F) a ⟹ α
x✝¹ : Fin2 n
x✝ : α x✝¹
⊢ x✝ ∈ supp (abs { fst := a, snd := f }) x✝¹ ↔ x✝ ∈ supp { fst := a, snd := f } x✝¹

Next tactic:
simp only [supp, h, mem_setOf_eq]
theorem liftpPreservation_iff_uniform : q.LiftPPreservation ↔ q.IsUniform := by
  

Proof state:
n : ℕ
F : TypeVec.{u} n → Type u_1
inst✝ : MvFunctor F
q : MvQPF F
⊢ LiftPPreservation ↔ IsUniform

Next tactic:
rw [← suppPreservation_iff_liftpPreservation, suppPreservation_iff_isUniform]
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  

Proof state:
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
⊢ Mono (app' φ 2)

Next tactic:
apply mono_of_cancel_zero
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  

Proof state:
case h
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
⊢ ∀ {P : C} (g : P ⟶ obj' R₁ 2), g ≫ app' φ 2 = 0 → g = 0

Next tactic:
intro A f₂ h₁
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  

Proof state:
case h
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
⊢ f₂ = 0

Next tactic:
have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    

Proof state:
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
⊢ f₂ ≫ map' R₁ 2 3 = 0

Next tactic:
rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  

Proof state:
case h
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
⊢ f₂ = 0

Next tactic:
obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  

Proof state:
case h.intro.intro.intro.intro
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝ : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ : π₁ ≫ f₂ = f₁ ≫ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).f
⊢ f₂ = 0

Next tactic:
dsimp at hf₁
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  dsimp at hf₁
  

Proof state:
case h.intro.intro.intro.intro
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝ : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ :
  π₁ ≫ f₂ = f₁ ≫ R₁.map (homOfLE (_ : { val := 1, isLt := (_ : 1 < 3 + 1) } ≤ { val := 2, isLt := (_ : 2 < 3 + 1) }))
⊢ f₂ = 0

Next tactic:
have h₃ : (f₁ ≫ app' φ 1) ≫ R₂.map' 1 2 = 0 := by
    rw [assoc, ← NatTrans.naturality, ← reassoc_of% hf₁, h₁, comp_zero]
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  dsimp at hf₁
  have h₃ : (f₁ ≫ app' φ 1) ≫ R₂.map' 1 2 = 0 := by
    

Proof state:
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝ : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ :
  π₁ ≫ f₂ = f₁ ≫ R₁.map (homOfLE (_ : { val := 1, isLt := (_ : 1 < 3 + 1) } ≤ { val := 2, isLt := (_ : 2 < 3 + 1) }))
⊢ (f₁ ≫ app' φ 1) ≫ map' R₂ 1 2 = 0

Next tactic:
rw [assoc, ← NatTrans.naturality, ← reassoc_of% hf₁, h₁, comp_zero]
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  dsimp at hf₁
  have h₃ : (f₁ ≫ app' φ 1) ≫ R₂.map' 1 2 = 0 := by
    rw [assoc, ← NatTrans.naturality, ← reassoc_of% hf₁, h₁, comp_zero]
  

Proof state:
case h.intro.intro.intro.intro
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃✝ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝ : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ :
  π₁ ≫ f₂ = f₁ ≫ R₁.map (homOfLE (_ : { val := 1, isLt := (_ : 1 < 3 + 1) } ≤ { val := 2, isLt := (_ : 2 < 3 + 1) }))
h₃ : (f₁ ≫ app' φ 1) ≫ map' R₂ 1 2 = 0
⊢ f₂ = 0

Next tactic:
obtain ⟨A₂, π₂, _, g₀, hg₀⟩ := (hR₂.exact 0).exact_up_to_refinements _ h₃
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  dsimp at hf₁
  have h₃ : (f₁ ≫ app' φ 1) ≫ R₂.map' 1 2 = 0 := by
    rw [assoc, ← NatTrans.naturality, ← reassoc_of% hf₁, h₁, comp_zero]
  obtain ⟨A₂, π₂, _, g₀, hg₀⟩ := (hR₂.exact 0).exact_up_to_refinements _ h₃
  

Proof state:
case h.intro.intro.intro.intro.intro.intro.intro.intro
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃✝ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝¹ : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ :
  π₁ ≫ f₂ = f₁ ≫ R₁.map (homOfLE (_ : { val := 1, isLt := (_ : 1 < 3 + 1) } ≤ { val := 2, isLt := (_ : 2 < 3 + 1) }))
h₃ : (f₁ ≫ app' φ 1) ≫ map' R₂ 1 2 = 0
A₂ : C
π₂ : A₂ ⟶ A₁
w✝ : Epi π₂
g₀ : A₂ ⟶ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).X₁
hg₀ :
  π₂ ≫ f₁ ≫ app' φ 1 = g₀ ≫ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).f
⊢ f₂ = 0

Next tactic:
obtain ⟨A₃, π₃, _, f₀, hf₀⟩ := surjective_up_to_refinements_of_epi (app' φ 0 _) g₀
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  dsimp at hf₁
  have h₃ : (f₁ ≫ app' φ 1) ≫ R₂.map' 1 2 = 0 := by
    rw [assoc, ← NatTrans.naturality, ← reassoc_of% hf₁, h₁, comp_zero]
  obtain ⟨A₂, π₂, _, g₀, hg₀⟩ := (hR₂.exact 0).exact_up_to_refinements _ h₃
  obtain ⟨A₃, π₃, _, f₀, hf₀⟩ := surjective_up_to_refinements_of_epi (app' φ 0 _) g₀
  

Proof state:
case h.intro.intro.intro.intro.intro.intro.intro.intro.intro.intro.intro.intro
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃✝ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝² : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ :
  π₁ ≫ f₂ = f₁ ≫ R₁.map (homOfLE (_ : { val := 1, isLt := (_ : 1 < 3 + 1) } ≤ { val := 2, isLt := (_ : 2 < 3 + 1) }))
h₃ : (f₁ ≫ app' φ 1) ≫ map' R₂ 1 2 = 0
A₂ : C
π₂ : A₂ ⟶ A₁
w✝¹ : Epi π₂
g₀ : A₂ ⟶ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).X₁
hg₀ :
  π₂ ≫ f₁ ≫ app' φ 1 = g₀ ≫ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).f
A₃ : C
π₃ : A₃ ⟶ A₂
w✝ : Epi π₃
f₀ : A₃ ⟶ obj' R₁ 0
hf₀ : π₃ ≫ g₀ = f₀ ≫ app' φ 0
⊢ f₂ = 0

Next tactic:
have h₄ : f₀ ≫ R₁.map' 0 1 = π₃ ≫ π₂ ≫ f₁ := by
    rw [← cancel_mono (app' φ 1 _), assoc, assoc, assoc, NatTrans.naturality,
      ← reassoc_of% hf₀, hg₀]
    rfl
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  dsimp at hf₁
  have h₃ : (f₁ ≫ app' φ 1) ≫ R₂.map' 1 2 = 0 := by
    rw [assoc, ← NatTrans.naturality, ← reassoc_of% hf₁, h₁, comp_zero]
  obtain ⟨A₂, π₂, _, g₀, hg₀⟩ := (hR₂.exact 0).exact_up_to_refinements _ h₃
  obtain ⟨A₃, π₃, _, f₀, hf₀⟩ := surjective_up_to_refinements_of_epi (app' φ 0 _) g₀
  have h₄ : f₀ ≫ R₁.map' 0 1 = π₃ ≫ π₂ ≫ f₁ := by
    

Proof state:
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃✝ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝² : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ :
  π₁ ≫ f₂ = f₁ ≫ R₁.map (homOfLE (_ : { val := 1, isLt := (_ : 1 < 3 + 1) } ≤ { val := 2, isLt := (_ : 2 < 3 + 1) }))
h₃ : (f₁ ≫ app' φ 1) ≫ map' R₂ 1 2 = 0
A₂ : C
π₂ : A₂ ⟶ A₁
w✝¹ : Epi π₂
g₀ : A₂ ⟶ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).X₁
hg₀ :
  π₂ ≫ f₁ ≫ app' φ 1 = g₀ ≫ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).f
A₃ : C
π₃ : A₃ ⟶ A₂
w✝ : Epi π₃
f₀ : A₃ ⟶ obj' R₁ 0
hf₀ : π₃ ≫ g₀ = f₀ ≫ app' φ 0
⊢ f₀ ≫ map' R₁ 0 1 = π₃ ≫ π₂ ≫ f₁

Next tactic:
rw [← cancel_mono (app' φ 1 _), assoc, assoc, assoc, NatTrans.naturality,
      ← reassoc_of% hf₀, hg₀]
theorem mono_of_epi_of_mono_of_mono' (hR₁ : R₁.map' 0 2 = 0)
    (hR₁' : (mk₂ (R₁.map' 1 2) (R₁.map' 2 3)).Exact)
    (hR₂ : (mk₂ (R₂.map' 0 1) (R₂.map' 1 2)).Exact)
    (h₀ : Epi (app' φ 0)) (h₁ : Mono (app' φ 1)) (h₃ : Mono (app' φ 3)) :
    Mono (app' φ 2) := by
  apply mono_of_cancel_zero
  intro A f₂ h₁
  have h₂ : f₂ ≫ R₁.map' 2 3 = 0 := by
    rw [← cancel_mono (app' φ 3 _), assoc, NatTrans.naturality, reassoc_of% h₁,
      zero_comp, zero_comp]
  obtain ⟨A₁, π₁, _, f₁, hf₁⟩ := (hR₁'.exact 0).exact_up_to_refinements f₂ h₂
  dsimp at hf₁
  have h₃ : (f₁ ≫ app' φ 1) ≫ R₂.map' 1 2 = 0 := by
    rw [assoc, ← NatTrans.naturality, ← reassoc_of% hf₁, h₁, comp_zero]
  obtain ⟨A₂, π₂, _, g₀, hg₀⟩ := (hR₂.exact 0).exact_up_to_refinements _ h₃
  obtain ⟨A₃, π₃, _, f₀, hf₀⟩ := surjective_up_to_refinements_of_epi (app' φ 0 _) g₀
  have h₄ : f₀ ≫ R₁.map' 0 1 = π₃ ≫ π₂ ≫ f₁ := by
    rw [← cancel_mono (app' φ 1 _), assoc, assoc, assoc, NatTrans.naturality,
      ← reassoc_of% hf₀, hg₀]
    

Proof state:
C : Type u_1
inst✝¹ : Category.{u_2, u_1} C
inst✝ : Abelian C
R₁ R₂ : ComposableArrows C 3
φ : R₁ ⟶ R₂
hR₁ : map' R₁ 0 2 = 0
hR₁' : ComposableArrows.Exact (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))
hR₂ : ComposableArrows.Exact (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))
h₀ : Epi (app' φ 0)
h₁✝ : Mono (app' φ 1)
h₃✝ : Mono (app' φ 3)
A : C
f₂ : A ⟶ obj' R₁ 2
h₁ : f₂ ≫ app' φ 2 = 0
h₂ : f₂ ≫ map' R₁ 2 3 = 0
A₁ : C
π₁ : A₁ ⟶ A
w✝² : Epi π₁
f₁ : A₁ ⟶ (sc (mk₂ (map' R₁ 1 2) (map' R₁ 2 3)) (_ : IsComplex (mk₂ (map' R₁ 1 2) (map' R₁ 2 3))) 0).X₁
hf₁ :
  π₁ ≫ f₂ = f₁ ≫ R₁.map (homOfLE (_ : { val := 1, isLt := (_ : 1 < 3 + 1) } ≤ { val := 2, isLt := (_ : 2 < 3 + 1) }))
h₃ : (f₁ ≫ app' φ 1) ≫ map' R₂ 1 2 = 0
A₂ : C
π₂ : A₂ ⟶ A₁
w✝¹ : Epi π₂
g₀ : A₂ ⟶ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).X₁
hg₀ :
  π₂ ≫ f₁ ≫ app' φ 1 = g₀ ≫ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).f
A₃ : C
π₃ : A₃ ⟶ A₂
w✝ : Epi π₃
f₀ : A₃ ⟶ obj' R₁ 0
hf₀ : π₃ ≫ g₀ = f₀ ≫ app' φ 0
⊢ π₃ ≫ g₀ ≫ R₂.map (homOfLE (_ : { val := 0, isLt := (_ : 0 < 3 + 1) } ≤ { val := 1, isLt := (_ : 1 < 3 + 1) })) =
    π₃ ≫ g₀ ≫ (sc (mk₂ (map' R₂ 0 1) (map' R₂ 1 2)) (_ : IsComplex (mk₂ (map' R₂ 0 1) (map' R₂ 1 2))) 0).f

Next tactic:
rfl