l3lab/ntp-mathlib huggingface dataset:
/-- The universal property of `𝕎 R` as projective limit of truncated Witt vector rings. -/
@[simps]
def liftEquiv : { f : ∀ k, S →+* TruncatedWittVector p k R // ∀ (k₁ k₂) (hk : k₁ ≤ k₂),
    (TruncatedWittVector.truncate hk).comp (f k₂) = f k₁ } ≃ (S →+* 𝕎 R) where
  toFun f := lift f.1 f.2
  invFun g :=
    ⟨fun k => (truncate k).comp g, by
      

Proof state:
p : ℕ
hp : Fact (Nat.Prime p)
n : ℕ
R : Type u_1
inst✝¹ : CommRing R
S : Type u_2
inst✝ : Semiring S
f : (k : ℕ) → S →+* TruncatedWittVector p k R
f_compat : ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂), RingHom.comp (TruncatedWittVector.truncate hk) (f k₂) = f k₁
g : S →+* 𝕎 R
⊢ ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂),
    RingHom.comp (TruncatedWittVector.truncate hk) ((fun k => RingHom.comp (truncate k) g) k₂) =
      (fun k => RingHom.comp (truncate k) g) k₁

Next tactic:
intro _ _ h
/-- The universal property of `𝕎 R` as projective limit of truncated Witt vector rings. -/
@[simps]
def liftEquiv : { f : ∀ k, S →+* TruncatedWittVector p k R // ∀ (k₁ k₂) (hk : k₁ ≤ k₂),
    (TruncatedWittVector.truncate hk).comp (f k₂) = f k₁ } ≃ (S →+* 𝕎 R) where
  toFun f := lift f.1 f.2
  invFun g :=
    ⟨fun k => (truncate k).comp g, by
      intro _ _ h
      

Proof state:
p : ℕ
hp : Fact (Nat.Prime p)
n : ℕ
R : Type u_1
inst✝¹ : CommRing R
S : Type u_2
inst✝ : Semiring S
f : (k : ℕ) → S →+* TruncatedWittVector p k R
f_compat : ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂), RingHom.comp (TruncatedWittVector.truncate hk) (f k₂) = f k₁
g : S →+* 𝕎 R
k₁✝ k₂✝ : ℕ
h : k₁✝ ≤ k₂✝
⊢ RingHom.comp (TruncatedWittVector.truncate h) ((fun k => RingHom.comp (truncate k) g) k₂✝) =
    (fun k => RingHom.comp (truncate k) g) k₁✝

Next tactic:
simp only [← RingHom.comp_assoc, truncate_comp_wittVector_truncate]
/-- The universal property of `𝕎 R` as projective limit of truncated Witt vector rings. -/
@[simps]
def liftEquiv : { f : ∀ k, S →+* TruncatedWittVector p k R // ∀ (k₁ k₂) (hk : k₁ ≤ k₂),
    (TruncatedWittVector.truncate hk).comp (f k₂) = f k₁ } ≃ (S →+* 𝕎 R) where
  toFun f := lift f.1 f.2
  invFun g :=
    ⟨fun k => (truncate k).comp g, by
      intro _ _ h
      simp only [← RingHom.comp_assoc, truncate_comp_wittVector_truncate]⟩
  left_inv := by 

Proof state:
p : ℕ
hp : Fact (Nat.Prime p)
n : ℕ
R : Type u_1
inst✝¹ : CommRing R
S : Type u_2
inst✝ : Semiring S
f : (k : ℕ) → S →+* TruncatedWittVector p k R
f_compat : ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂), RingHom.comp (TruncatedWittVector.truncate hk) (f k₂) = f k₁
⊢ Function.LeftInverse
    (fun g =>
      { val := fun k => RingHom.comp (truncate k) g,
        property :=
          (_ :
            ∀ (k₁ k₂ : ℕ) (h : k₁ ≤ k₂),
              RingHom.comp (RingHom.comp (TruncatedWittVector.truncate h) (truncate k₂)) g =
                RingHom.comp (truncate k₁) g) })
    fun f => lift ↑f (_ : ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂), RingHom.comp (TruncatedWittVector.truncate hk) (↑f k₂) = ↑f k₁)

Next tactic:
rintro ⟨f, hf⟩
/-- The universal property of `𝕎 R` as projective limit of truncated Witt vector rings. -/
@[simps]
def liftEquiv : { f : ∀ k, S →+* TruncatedWittVector p k R // ∀ (k₁ k₂) (hk : k₁ ≤ k₂),
    (TruncatedWittVector.truncate hk).comp (f k₂) = f k₁ } ≃ (S →+* 𝕎 R) where
  toFun f := lift f.1 f.2
  invFun g :=
    ⟨fun k => (truncate k).comp g, by
      intro _ _ h
      simp only [← RingHom.comp_assoc, truncate_comp_wittVector_truncate]⟩
  left_inv := by rintro ⟨f, hf⟩; 

Proof state:
case mk
p : ℕ
hp : Fact (Nat.Prime p)
n : ℕ
R : Type u_1
inst✝¹ : CommRing R
S : Type u_2
inst✝ : Semiring S
f✝ : (k : ℕ) → S →+* TruncatedWittVector p k R
f_compat : ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂), RingHom.comp (TruncatedWittVector.truncate hk) (f✝ k₂) = f✝ k₁
f : (k : ℕ) → S →+* TruncatedWittVector p k R
hf : ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂), RingHom.comp (TruncatedWittVector.truncate hk) (f k₂) = f k₁
⊢ (fun g =>
        { val := fun k => RingHom.comp (truncate k) g,
          property :=
            (_ :
              ∀ (k₁ k₂ : ℕ) (h : k₁ ≤ k₂),
                RingHom.comp (RingHom.comp (TruncatedWittVector.truncate h) (truncate k₂)) g =
                  RingHom.comp (truncate k₁) g) })
      ((fun f =>
          lift ↑f (_ : ∀ (k₁ k₂ : ℕ) (hk : k₁ ≤ k₂), RingHom.comp (TruncatedWittVector.truncate hk) (↑f k₂) = ↑f k₁))
        { val := f, property := hf }) =
    { val := f, property := hf }

Next tactic:
simp only [truncate_comp_lift]
/-- Pull back a term of `Meq P S` with respect to a morphism `f : Y ⟶ X` in `C`. -/
def pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    Meq P ((J.pullback f).obj S) :=
  ⟨fun I => x ⟨_, I.f ≫ f, I.hf⟩, fun I =>
    x.condition
      ⟨I.Y₁, I.Y₂, I.Z, I.g₁, I.g₂, I.f₁ ≫ f, I.f₂ ≫ f, I.h₁, I.h₂, by 

Proof state:
C : Type u
inst✝² : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝¹ : Category.{max v u, w} D
inst✝ : ConcreteCategory D
Y X : C
P : Cᵒᵖ ⥤ D
S : GrothendieckTopology.Cover J X
x : Meq P S
f : Y ⟶ X
I : GrothendieckTopology.Cover.Relation ((GrothendieckTopology.pullback J f).obj S)
⊢ I.g₁ ≫ I.f₁ ≫ f = I.g₂ ≫ I.f₂ ≫ f

Next tactic:
simp [I.w_assoc]
/-- Make a term of `Meq P S`. -/
def mk {X : C} {P : Cᵒᵖ ⥤ D} (S : J.Cover X) (x : P.obj (op X)) : Meq P S :=
  ⟨fun I => P.map I.f.op x, fun I => by
    

Proof state:
C : Type u
inst✝² : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝¹ : Category.{max v u, w} D
inst✝ : ConcreteCategory D
X : C
P : Cᵒᵖ ⥤ D
S : GrothendieckTopology.Cover J X
x : (forget D).obj (P.obj (op X))
I : GrothendieckTopology.Cover.Relation S
⊢ (P.map I.g₁.op) ((fun I => (P.map I.f.op) x) (GrothendieckTopology.Cover.Relation.fst I)) =
    (P.map I.g₂.op) ((fun I => (P.map I.f.op) x) (GrothendieckTopology.Cover.Relation.snd I))

Next tactic:
dsimp
/-- Make a term of `Meq P S`. -/
def mk {X : C} {P : Cᵒᵖ ⥤ D} (S : J.Cover X) (x : P.obj (op X)) : Meq P S :=
  ⟨fun I => P.map I.f.op x, fun I => by
    dsimp
    

Proof state:
C : Type u
inst✝² : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝¹ : Category.{max v u, w} D
inst✝ : ConcreteCategory D
X : C
P : Cᵒᵖ ⥤ D
S : GrothendieckTopology.Cover J X
x : (forget D).obj (P.obj (op X))
I : GrothendieckTopology.Cover.Relation S
⊢ (P.map I.g₁.op) ((P.map I.f₁.op) x) = (P.map I.g₂.op) ((P.map I.f₂.op) x)

Next tactic:
simp only [← comp_apply, ← P.map_comp, ← op_comp, I.w]
@[simp]
theorem equiv_symm_eq_apply {X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} [HasMultiequalizer (S.index P)]
    (x : Meq P S) (I : S.Arrow) :
    Multiequalizer.ι (S.index P) I ((Meq.equiv P S).symm x) = x I := by
  

Proof state:
C : Type u
inst✝⁴ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝³ : Category.{max v u, w} D
inst✝² : ConcreteCategory D
inst✝¹ : PreservesLimits (forget D)
X : C
P : Cᵒᵖ ⥤ D
S : GrothendieckTopology.Cover J X
inst✝ : HasMultiequalizer (GrothendieckTopology.Cover.index S P)
x : Meq P S
I : GrothendieckTopology.Cover.Arrow S
⊢ (Multiequalizer.ι (GrothendieckTopology.Cover.index S P) I) ((equiv P S).symm x) = ↑x I

Next tactic:
rw [← equiv_apply]
@[simp]
theorem equiv_symm_eq_apply {X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} [HasMultiequalizer (S.index P)]
    (x : Meq P S) (I : S.Arrow) :
    Multiequalizer.ι (S.index P) I ((Meq.equiv P S).symm x) = x I := by
  rw [← equiv_apply]
  

Proof state:
C : Type u
inst✝⁴ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝³ : Category.{max v u, w} D
inst✝² : ConcreteCategory D
inst✝¹ : PreservesLimits (forget D)
X : C
P : Cᵒᵖ ⥤ D
S : GrothendieckTopology.Cover J X
inst✝ : HasMultiequalizer (GrothendieckTopology.Cover.index S P)
x : Meq P S
I : GrothendieckTopology.Cover.Arrow S
⊢ ↑((equiv P S) ((equiv P S).symm x)) I = ↑x I

Next tactic:
simp
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
⊢ ((plusObj J P).map f.op) (mk x) = mk (Meq.pullback x f)

Next tactic:
dsimp [mk, plusObj]
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
⊢ (colimMap (diagramPullback J P f) ≫ colimit.pre (diagram J P Y) (pullback J f).op)
      ((colimit.ι (diagram J P X) (op S)) ((Meq.equiv P S).symm x)) =
    (colimit.ι (diagram J P Y) (op (Cover.pullback S f))) ((Meq.equiv P (Cover.pullback S f)).symm (Meq.pullback x f))

Next tactic:
rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
⊢ (colimit.ι (diagram J P Y) ((pullback J f).op.obj (op S)))
      (((diagramPullback J P f).app (op S)) ((Meq.equiv P S).symm x)) =
    (colimit.ι (diagram J P Y) (op (Cover.pullback S f))) ((Meq.equiv P (Cover.pullback S f)).symm (Meq.pullback x f))

Next tactic:
apply congr_arg
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  apply congr_arg
  

Proof state:
case h
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
⊢ ((diagramPullback J P f).app (op S)) ((Meq.equiv P S).symm x) =
    (Meq.equiv P (Cover.pullback S f)).symm (Meq.pullback x f)

Next tactic:
apply (Meq.equiv P _).injective
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  apply congr_arg
  apply (Meq.equiv P _).injective
  

Proof state:
case h.a
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
⊢ (Meq.equiv P ((pullback J f).op.obj (op S)).unop) (((diagramPullback J P f).app (op S)) ((Meq.equiv P S).symm x)) =
    (Meq.equiv P ((pullback J f).op.obj (op S)).unop) ((Meq.equiv P (Cover.pullback S f)).symm (Meq.pullback x f))

Next tactic:
erw [Equiv.apply_symm_apply]
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  apply congr_arg
  apply (Meq.equiv P _).injective
  erw [Equiv.apply_symm_apply]
  

Proof state:
case h.a
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
⊢ (Meq.equiv P ((pullback J f).op.obj (op S)).unop) (((diagramPullback J P f).app (op S)) ((Meq.equiv P S).symm x)) =
    Meq.pullback x f

Next tactic:
ext i
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  apply congr_arg
  apply (Meq.equiv P _).injective
  erw [Equiv.apply_symm_apply]
  ext i
  

Proof state:
case h.a.h
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
i : Cover.Arrow ((pullback J f).op.obj (op S)).unop
⊢ ↑((Meq.equiv P ((pullback J f).op.obj (op S)).unop) (((diagramPullback J P f).app (op S)) ((Meq.equiv P S).symm x)))
      i =
    ↑(Meq.pullback x f) i

Next tactic:
simp only [Functor.op_obj, unop_op, pullback_obj, diagram_obj, Functor.comp_obj,
    diagramPullback_app, Meq.equiv_apply, Meq.pullback_apply]
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  apply congr_arg
  apply (Meq.equiv P _).injective
  erw [Equiv.apply_symm_apply]
  ext i
  simp only [Functor.op_obj, unop_op, pullback_obj, diagram_obj, Functor.comp_obj,
    diagramPullback_app, Meq.equiv_apply, Meq.pullback_apply]
  

Proof state:
case h.a.h
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
i : Cover.Arrow ((pullback J f).op.obj (op S)).unop
⊢ (Multiequalizer.ι (Cover.index (Cover.pullback S f) P) i)
      ((Multiequalizer.lift (Cover.index ((pullback J f).op.obj (op S)).unop P) ((diagram J P X).obj (op S))
          (fun I => Multiequalizer.ι (Cover.index S P) (Cover.Arrow.base I))
          (_ :
            ∀ (b : (Cover.index ((pullback J f).op.obj (op S)).unop P).R),
              (fun I => Multiequalizer.ι (Cover.index S P) (Cover.Arrow.base I))
                    (MulticospanIndex.fstTo (Cover.index ((pullback J f).op.obj (op S)).unop P) b) ≫
                  MulticospanIndex.fst (Cover.index ((pullback J f).op.obj (op S)).unop P) b =
                (fun I => Multiequalizer.ι (Cover.index S P) (Cover.Arrow.base I))
                    (MulticospanIndex.sndTo (Cover.index ((pullback J f).op.obj (op S)).unop P) b) ≫
                  MulticospanIndex.snd (Cover.index ((pullback J f).op.obj (op S)).unop P) b))
        ((Meq.equiv P S).symm x)) =
    ↑x { Y := i.Y, f := i.f ≫ f, hf := (_ : (Cover.sieve (Cover.pullback S f)).arrows i.f) }

Next tactic:
erw [← comp_apply, Multiequalizer.lift_ι, Meq.equiv_symm_eq_apply]
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  apply congr_arg
  apply (Meq.equiv P _).injective
  erw [Equiv.apply_symm_apply]
  ext i
  simp only [Functor.op_obj, unop_op, pullback_obj, diagram_obj, Functor.comp_obj,
    diagramPullback_app, Meq.equiv_apply, Meq.pullback_apply]
  erw [← comp_apply, Multiequalizer.lift_ι, Meq.equiv_symm_eq_apply]
  

Proof state:
case h.a.h
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
i : Cover.Arrow ((pullback J f).op.obj (op S)).unop
⊢ ↑x (Cover.Arrow.base i) = ↑x { Y := i.Y, f := i.f ≫ f, hf := (_ : (Cover.sieve (Cover.pullback S f)).arrows i.f) }

Next tactic:
cases i
theorem res_mk_eq_mk_pullback {Y X : C} {P : Cᵒᵖ ⥤ D} {S : J.Cover X} (x : Meq P S) (f : Y ⟶ X) :
    (J.plusObj P).map f.op (mk x) = mk (x.pullback f) := by
  dsimp [mk, plusObj]
  rw [← comp_apply (x := (Meq.equiv P S).symm x), ι_colimMap_assoc, colimit.ι_pre,
    comp_apply (x := (Meq.equiv P S).symm x)]
  apply congr_arg
  apply (Meq.equiv P _).injective
  erw [Equiv.apply_symm_apply]
  ext i
  simp only [Functor.op_obj, unop_op, pullback_obj, diagram_obj, Functor.comp_obj,
    diagramPullback_app, Meq.equiv_apply, Meq.pullback_apply]
  erw [← comp_apply, Multiequalizer.lift_ι, Meq.equiv_symm_eq_apply]
  cases i; 

Proof state:
case h.a.h.mk
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
Y X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : Meq P S
f : Y ⟶ X
Y✝ : C
f✝ : Y✝ ⟶ Y
hf✝ : (Cover.sieve ((pullback J f).op.obj (op S)).unop).arrows f✝
⊢ ↑x (Cover.Arrow.base { Y := Y✝, f := f✝, hf := hf✝ }) =
    ↑x
      { Y := { Y := Y✝, f := f✝, hf := hf✝ }.Y, f := { Y := Y✝, f := f✝, hf := hf✝ }.f ≫ f,
        hf := (_ : (Cover.sieve (Cover.pullback S f)).arrows { Y := Y✝, f := f✝, hf := hf✝ }.f) }

Next tactic:
rfl
theorem toPlus_mk {X : C} {P : Cᵒᵖ ⥤ D} (S : J.Cover X) (x : P.obj (op X)) :
    (J.toPlus P).app _ x = mk (Meq.mk S x) := by
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : (forget D).obj (P.obj (op X))
⊢ ((toPlus J P).app (op X)) x = mk (Meq.mk S x)

Next tactic:
dsimp [mk, toPlus]
theorem toPlus_mk {X : C} {P : Cᵒᵖ ⥤ D} (S : J.Cover X) (x : P.obj (op X)) :
    (J.toPlus P).app _ x = mk (Meq.mk S x) := by
  dsimp [mk, toPlus]
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : (forget D).obj (P.obj (op X))
⊢ (Cover.toMultiequalizer ⊤ P ≫ colimit.ι (diagram J P X) (op ⊤)) x =
    (colimit.ι (diagram J P X) (op S)) ((Meq.equiv P S).symm (Meq.mk S x))

Next tactic:
let e : S ⟶ ⊤ := homOfLE (OrderTop.le_top _)
theorem toPlus_mk {X : C} {P : Cᵒᵖ ⥤ D} (S : J.Cover X) (x : P.obj (op X)) :
    (J.toPlus P).app _ x = mk (Meq.mk S x) := by
  dsimp [mk, toPlus]
  let e : S ⟶ ⊤ := homOfLE (OrderTop.le_top _)
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : (forget D).obj (P.obj (op X))
e : S ⟶ ⊤ := homOfLE (_ : S ≤ ⊤)
⊢ (Cover.toMultiequalizer ⊤ P ≫ colimit.ι (diagram J P X) (op ⊤)) x =
    (colimit.ι (diagram J P X) (op S)) ((Meq.equiv P S).symm (Meq.mk S x))

Next tactic:
rw [← colimit.w _ e.op]
theorem toPlus_mk {X : C} {P : Cᵒᵖ ⥤ D} (S : J.Cover X) (x : P.obj (op X)) :
    (J.toPlus P).app _ x = mk (Meq.mk S x) := by
  dsimp [mk, toPlus]
  let e : S ⟶ ⊤ := homOfLE (OrderTop.le_top _)
  rw [← colimit.w _ e.op]
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : (forget D).obj (P.obj (op X))
e : S ⟶ ⊤ := homOfLE (_ : S ≤ ⊤)
⊢ (Cover.toMultiequalizer ⊤ P ≫ (diagram J P X).map e.op ≫ colimit.ι (diagram J P X) (op S)) x =
    (colimit.ι (diagram J P X) (op S)) ((Meq.equiv P S).symm (Meq.mk S x))

Next tactic:
delta Cover.toMultiequalizer
theorem toPlus_mk {X : C} {P : Cᵒᵖ ⥤ D} (S : J.Cover X) (x : P.obj (op X)) :
    (J.toPlus P).app _ x = mk (Meq.mk S x) := by
  dsimp [mk, toPlus]
  let e : S ⟶ ⊤ := homOfLE (OrderTop.le_top _)
  rw [← colimit.w _ e.op]
  delta Cover.toMultiequalizer
  

Proof state:
C : Type u
inst✝⁵ : Category.{v, u} C
J : GrothendieckTopology C
D : Type w
inst✝⁴ : Category.{max v u, w} D
inst✝³ : ConcreteCategory D
inst✝² : PreservesLimits (forget D)
inst✝¹ : ∀ (X : C), HasColimitsOfShape (Cover J X)ᵒᵖ D
inst✝ : ∀ (P : Cᵒᵖ ⥤ D) (X : C) (S : Cover J X), HasMultiequalizer (Cover.index S P)
X : C
P : Cᵒᵖ ⥤ D
S : Cover J X
x : (forget D).obj (P.obj (op X))
e : S ⟶ ⊤ := homOfLE (_ : S ≤ ⊤)
⊢ (Multiequalizer.lift (Cover.index ⊤ P) (P.obj (op X)) (fun I => P.map I.f.op)
          (_ :
            ∀ (I : (Cover.index ⊤ P).R),
              (fun I => P.map I.f.op) (MulticospanIndex.fstTo (Cover.index ⊤ P) I) ≫
                  MulticospanIndex.fst (Cover.index ⊤ P) I =
                (fun I => P.map I.f.op) (MulticospanIndex.sndTo (Cover.index ⊤ P) I) ≫
                  MulticospanIndex.snd (Cover.index ⊤ P) I) ≫
        (diagram J P X).map e.op ≫ colimit.ι (diagram J P X) (op S))
      x =
    (colimit.ι (diagram J P X) (op S)) ((Meq.equiv P S).symm (Meq.mk S x))

Next tactic:
erw [comp_apply, comp_apply]