Skip to content

Commit

Permalink
feat(category_theory/limits): is_limit.exists_unique (#11875)
Browse files Browse the repository at this point in the history
Yet another restatement of the limit property which is occasionally useful.
  • Loading branch information
TwoFX committed Feb 7, 2022
1 parent 556483f commit dcbb59c
Show file tree
Hide file tree
Showing 3 changed files with 58 additions and 1 deletion.
8 changes: 8 additions & 0 deletions src/category_theory/limits/has_limits.lean
Expand Up @@ -189,6 +189,10 @@ is_limit.cone_point_unique_up_to_iso_hom_comp _ _ _
(is_limit.cone_point_unique_up_to_iso (limit.is_limit _) hc).inv ≫ limit.π F j = c.π.app j :=
is_limit.cone_point_unique_up_to_iso_inv_comp _ _ _

lemma limit.exists_unique {F : J ⥤ C} [has_limit F] (t : cone F) :
∃! (l : t.X ⟶ limit F), ∀ j, l ≫ limit.π F j = t.π.app j :=
(limit.is_limit F).exists_unique _

/--
Given any other limit cone for `F`, the chosen `limit F` is isomorphic to the cone point.
-/
Expand Down Expand Up @@ -636,6 +640,10 @@ is_colimit.comp_cocone_point_unique_up_to_iso_hom _ _ _
c.ι.app j :=
is_colimit.comp_cocone_point_unique_up_to_iso_inv _ _ _

lemma colimit.exists_unique {F : J ⥤ C} [has_colimit F] (t : cocone F) :
∃! (d : colimit F ⟶ t.X), ∀ j, colimit.ι F j ≫ d = t.ι.app j :=
(colimit.is_colimit F).exists_unique _

/--
Given any other colimit cocone for `F`, the chosen `colimit F` is isomorphic to the cocone point.
-/
Expand Down
22 changes: 21 additions & 1 deletion src/category_theory/limits/is_limit.lean
Expand Up @@ -17,7 +17,7 @@ it is repeated, with slightly different names, for colimits.
The main structures defined in this file is
* `is_limit c`, for `c : cone F`, `F : J ⥤ C`, expressing that `c` is a limit cone,
See also `category_theory.limits.limits` which further builds:
See also `category_theory.limits.has_limits` which further builds:
* `limit_cone F`, which consists of a choice of cone for `F` and the fact it is a limit cone, and
* `has_limit F`, asserting the mere existence of some limit cone for `F`.
Expand Down Expand Up @@ -92,6 +92,16 @@ lemma uniq_cone_morphism {s t : cone F} (h : is_limit t) {f f' : s ⟶ t} :
have ∀ {g : s ⟶ t}, g = h.lift_cone_morphism s, by intro g; ext; exact h.uniq _ _ g.w,
this.trans this.symm

/-- Restating the definition of a limit cone in terms of the ∃! operator. -/
lemma exists_unique {t : cone F} (h : is_limit t) (s : cone F) :
∃! (l : s.X ⟶ t.X), ∀ j, l ≫ t.π.app j = s.π.app j :=
⟨h.lift s, h.fac s, h.uniq s⟩

/-- Noncomputably make a colimit cocone from the existence of unique factorizations. -/
def of_exists_unique {t : cone F}
(ht : ∀ s : cone F, ∃! l : s.X ⟶ t.X, ∀ j, l ≫ t.π.app j = s.π.app j) : is_limit t :=
by { choose s hs hs' using ht, exact ⟨s, hs, hs'⟩ }

/--
Alternative constructor for `is_limit`,
providing a morphism of cones rather than a morphism between the cone points
Expand Down Expand Up @@ -523,6 +533,16 @@ lemma uniq_cocone_morphism {s t : cocone F} (h : is_colimit t) {f f' : t ⟶ s}
have ∀ {g : t ⟶ s}, g = h.desc_cocone_morphism s, by intro g; ext; exact h.uniq _ _ g.w,
this.trans this.symm

/-- Restating the definition of a colimit cocone in terms of the ∃! operator. -/
lemma exists_unique {t : cocone F} (h : is_colimit t) (s : cocone F) :
∃! (d : t.X ⟶ s.X), ∀ j, t.ι.app j ≫ d = s.ι.app j :=
⟨h.desc s, h.fac s, h.uniq s⟩

/-- Noncomputably make a colimit cocone from the existence of unique factorizations. -/
def of_exists_unique {t : cocone F}
(ht : ∀ s : cocone F, ∃! d : t.X ⟶ s.X, ∀ j, t.ι.app j ≫ d = s.ι.app j) : is_colimit t :=
by { choose s hs hs' using ht, exact ⟨s, hs, hs'⟩ }

/--
Alternative constructor for `is_colimit`,
providing a morphism of cocones rather than a morphism between the cocone points
Expand Down
29 changes: 29 additions & 0 deletions src/category_theory/limits/shapes/equalizers.lean
Expand Up @@ -304,6 +304,17 @@ def cofork.is_colimit.desc' {s : cofork f g} (hs : is_colimit s) {W : C} (k : Y
(h : f ≫ k = g ≫ k) : {l : s.X ⟶ W // cofork.π s ≫ l = k} :=
⟨hs.desc $ cofork.of_π _ h, hs.fac _ _⟩

lemma fork.is_limit.exists_unique {s : fork f g} (hs : is_limit s) {W : C} (k : W ⟶ X)
(h : k ≫ f = k ≫ g) : ∃! (l : W ⟶ s.X), l ≫ fork.ι s = k :=
⟨hs.lift $ fork.of_ι _ h, hs.fac _ _, λ m hm, fork.is_limit.hom_ext hs $
hm.symm ▸ (hs.fac (fork.of_ι _ h) walking_parallel_pair.zero).symm⟩

lemma cofork.is_colimit.exists_unique {s : cofork f g} (hs : is_colimit s) {W : C} (k : Y ⟶ W)
(h : f ≫ k = g ≫ k) : ∃! (d : s.X ⟶ W), cofork.π s ≫ d = k :=
⟨hs.desc $ cofork.of_π _ h, hs.fac _ _, λ m hm, cofork.is_colimit.hom_ext hs $
hm.symm ▸ (hs.fac (cofork.of_π _ h) walking_parallel_pair.one).symm⟩


/-- This is a slightly more convenient method to verify that a fork is a limit cone. It
only asks for a proof of facts that carry any mathematical content -/
def fork.is_limit.mk (t : fork f g)
Expand Down Expand Up @@ -352,6 +363,16 @@ cofork.is_colimit.mk t
(λ s, (create s).2.1)
(λ s m w, (create s).2.2 (w one))

/-- Noncomputably make a limit cone from the existence of unique factorizations. -/
def fork.is_limit.of_exists_unique {t : fork f g}
(hs : ∀ (s : fork f g), ∃! l : s.X ⟶ t.X, l ≫ fork.ι t = fork.ι s) : is_limit t :=
by { choose d hd hd' using hs, exact fork.is_limit.mk _ d hd (λ s m hm, hd' _ _ (hm _)) }

/-- Noncomputably make a colimit cocone from the existence of unique factorizations. -/
def cofork.is_colimit.of_exists_unique {t : cofork f g}
(hs : ∀ (s : cofork f g), ∃! d : t.X ⟶ s.X, cofork.π t ≫ d = cofork.π s) : is_colimit t :=
by { choose d hd hd' using hs, exact cofork.is_colimit.mk _ d hd (λ s m hm, hd' _ _ (hm _)) }

/--
Given a limit cone for the pair `f g : X ⟶ Y`, for any `Z`, morphisms from `Z` to its point are in
bijection with morphisms `h : Z ⟶ X` such that `h ≫ f = h ≫ g`.
Expand Down Expand Up @@ -559,6 +580,10 @@ def equalizer.lift' {W : C} (k : W ⟶ X) (h : k ≫ f = k ≫ g) :
(h : k ≫ equalizer.ι f g = l ≫ equalizer.ι f g) : k = l :=
fork.is_limit.hom_ext (limit.is_limit _) h

lemma equalizer.exists_unique {W : C} (k : W ⟶ X) (h : k ≫ f = k ≫ g) :
∃! (l : W ⟶ equalizer f g), l ≫ equalizer.ι f g = k :=
fork.is_limit.exists_unique (limit.is_limit _) _ h

/-- An equalizer morphism is a monomorphism -/
instance equalizer.ι_mono : mono (equalizer.ι f g) :=
{ right_cancellation := λ Z h k w, equalizer.hom_ext w }
Expand Down Expand Up @@ -691,6 +716,10 @@ def coequalizer.desc' {W : C} (k : Y ⟶ W) (h : f ≫ k = g ≫ k) :
(h : coequalizer.π f g ≫ k = coequalizer.π f g ≫ l) : k = l :=
cofork.is_colimit.hom_ext (colimit.is_colimit _) h

lemma coequalizer.exists_unique {W : C} (k : Y ⟶ W) (h : f ≫ k = g ≫ k) :
∃! (d : coequalizer f g ⟶ W), coequalizer.π f g ≫ d = k :=
cofork.is_colimit.exists_unique (colimit.is_colimit _) _ h

/-- A coequalizer morphism is an epimorphism -/
instance coequalizer.π_epi : epi (coequalizer.π f g) :=
{ left_cancellation := λ Z h k w, coequalizer.hom_ext w }
Expand Down

0 comments on commit dcbb59c

Please sign in to comment.