Theorem: CategoryTheory.IsKernelPair.cancel_right
File: Mathlib/CategoryTheory/Limits/Shapes/KernelPair.lean

tactic: let s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk s.fst s.snd (s.condition_assoc _)
state_before: C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
⊢ { l //
    l ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s ∧
      l ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s ∧
        ∀ {m : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt},
          m ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s →
            m ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s → m = l }

tactic: refine' ⟨big_k.isLimit.lift s', big_k.isLimit.fac _ WalkingCospan.left,
  big_k.isLimit.fac _ WalkingCospan.right, fun m₁ m₂ => _⟩
state_before: C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
⊢ { l //
    l ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s ∧
      l ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s ∧
        ∀ {m : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt},
          m ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s →
            m ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s → m = l }

tactic: apply big_k.isLimit.hom_ext
state_before: C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ = IsLimit.lift (IsPullback.isLimit big_k) s'

tactic: refine' (PullbackCone.mk a b _ : PullbackCone (f₁ ≫ f₂) _).equalizer_ext _ _
state_before: C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ ∀ (j : WalkingCospan),
    m✝ ≫ (IsPullback.cone big_k).π.app j = IsLimit.lift (IsPullback.isLimit big_k) s' ≫ (IsPullback.cone big_k).π.app j

tactic: . apply reassoc_of% comm
state_before: case refine'_1
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂

case refine'_2
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ ≫ PullbackCone.fst (PullbackCone.mk a b ?refine'_1) =
    IsLimit.lift (IsPullback.isLimit big_k) s' ≫ PullbackCone.fst (PullbackCone.mk a b ?refine'_1)

case refine'_3
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ ≫ PullbackCone.snd (PullbackCone.mk a b ?refine'_1) =
    IsLimit.lift (IsPullback.isLimit big_k) s' ≫ PullbackCone.snd (PullbackCone.mk a b ?refine'_1)

tactic: . apply m₁.trans (big_k.isLimit.fac s' WalkingCospan.left).symm
state_before: case refine'_2
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂)) =
    IsLimit.lift (IsPullback.isLimit big_k) s' ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂))

case refine'_3
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂)) =
    IsLimit.lift (IsPullback.isLimit big_k) s' ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂))

tactic: . apply m₂.trans (big_k.isLimit.fac s' WalkingCospan.right).symm
state_before: case refine'_3
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂)) =
    IsLimit.lift (IsPullback.isLimit big_k) s' ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂))

tactic: apply reassoc_of% comm
state_before: case refine'_1
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂

tactic: apply m₁.trans (big_k.isLimit.fac s' WalkingCospan.left).symm
state_before: case refine'_2
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂)) =
    IsLimit.lift (IsPullback.isLimit big_k) s' ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂))

tactic: apply m₂.trans (big_k.isLimit.fac s' WalkingCospan.right).symm
state_before: case refine'_3
C : Type u
inst✝ : Category C
R X Y Z : C
f : X ⟶ Y
a b : R ⟶ X
f₁ : X ⟶ Y
f₂ : Y ⟶ Z
comm : a ≫ f₁ = b ≫ f₁
big_k : IsKernelPair (f₁ ≫ f₂) a b
s : PullbackCone f₁ f₁
s' : PullbackCone (f₁ ≫ f₂) (f₁ ≫ f₂) :=
  PullbackCone.mk (PullbackCone.fst s) (PullbackCone.snd s)
    (_ : PullbackCone.fst s ≫ f₁ ≫ f₂ = PullbackCone.snd s ≫ f₁ ≫ f₂)
m✝ : s.pt ⟶ (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)).pt
m₁ : m✝ ≫ PullbackCone.fst (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.fst s
m₂ : m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ = b ≫ f₁)) = PullbackCone.snd s
⊢ m✝ ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂)) =
    IsLimit.lift (IsPullback.isLimit big_k) s' ≫ PullbackCone.snd (PullbackCone.mk a b (_ : a ≫ f₁ ≫ f₂ = b ≫ f₁ ≫ f₂))