Skip to content

Commit 1a5bbc7

Browse files
committed
feat(Topology): more API for ZerothHomotopy (leanprover-community#38201)
This PR introduces a very basic API for `ZerothHomotopy`. As it was not very well typed, the generic constructor `⟦x⟧` for quotients is replaced by a specific constructor `ZerothHomotopy.mk`.
1 parent bb88d2c commit 1a5bbc7

2 files changed

Lines changed: 48 additions & 16 deletions

File tree

Mathlib/Topology/Connected/LocPathConnected.lean

Lines changed: 5 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,7 @@ def connectedComponentsEquivZerothHomotopy : ConnectedComponents X ≃ ZerothHom
126126

127127
@[simp]
128128
lemma connectedComponentsEquivZerothHomotopy_apply (x : X) :
129-
connectedComponentsEquivZerothHomotopy ⟦x⟧ = ⟦x⟧ :=
129+
connectedComponentsEquivZerothHomotopy ⟦x⟧ = (.mk x) :=
130130
rfl
131131

132132
@[simp]
@@ -135,7 +135,7 @@ lemma coe_connectedComponentsEquivZerothHomotopy_symm :
135135
rfl
136136

137137
lemma connectedComponentsEquivZerothHomotopy_symm_apply (x : X) :
138-
connectedComponentsEquivZerothHomotopy.symm ⟦x⟧ = ⟦x⟧ :=
138+
connectedComponentsEquivZerothHomotopy.symm (.mk x) = ⟦x⟧ :=
139139
rfl
140140

141141
theorem pathConnected_subset_basis {U : Set X} (h : IsOpen U) (hx : x ∈ U) :
@@ -262,19 +262,12 @@ instance AlexandrovDiscrete.locPathConnectedSpace [AlexandrovDiscrete X] :
262262
symm
263263
apply hy.joinedIn <;> rewrite [mem_nhdsKer_singleton] <;> [assumption; rfl]
264264

265-
set_option backward.isDefEq.respectTransparency false in
266265
/-- If a space is locally path-connected, the topology of its path components is discrete. -/
267266
instance : DiscreteTopology <| ZerothHomotopy X := by
268267
refine discreteTopology_iff_isOpen_singleton.mpr fun c ↦ ?_
269-
obtain ⟨x, rfl⟩ := Quotient.mk_surjective c
270-
rw [← isQuotientMap_quotient_mk'.isOpen_preimage]
271-
#adaptation_note /-- Before https://github.com/leanprover/lean4/pull/13166
272-
(replacing grind's canonicalizer with a type-directed normalizer), `grind` closed this goal.
273-
It is not yet clear whether this is due to defeq abuse in Mathlib or a problem in the new
274-
canonicalizer; a minimization would help. The original proof was:
275-
`grind [ZerothHomotopy.preimage_singleton_eq_pathComponent, IsOpen.pathComponent]` -/
276-
rw [ZerothHomotopy.preimage_singleton_eq_pathComponent]
277-
exact IsOpen.pathComponent x
268+
obtain ⟨x, rfl⟩ := ZerothHomotopy.mk_surjective c
269+
rw [← ZerothHomotopy.isQuotientMap_mk.isOpen_preimage]
270+
grind [ZerothHomotopy.preimage_singleton_eq_pathComponent, IsOpen.pathComponent]
278271

279272
/-- A locally path-connected compact space has finitely many path components. -/
280273
instance [CompactSpace X] : Finite <| ZerothHomotopy X :=

Mathlib/Topology/Connected/PathConnected.lean

Lines changed: 43 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -108,13 +108,52 @@ def pathSetoid : Setoid X where
108108
def ZerothHomotopy :=
109109
Quotient (pathSetoid X)
110110

111+
namespace ZerothHomotopy
112+
113+
variable {X}
114+
115+
/-- The map `X → ZerothHomotopy X`. -/
116+
def mk (x : X) : ZerothHomotopy X := Quotient.mk _ x
117+
118+
lemma mk_surjective : Function.Surjective (mk (X := X)) := by
119+
rintro ⟨x⟩
120+
exact ⟨x, rfl⟩
121+
122+
@[elab_as_elim, induction_eliminator, cases_eliminator]
123+
lemma rec {motive : ZerothHomotopy X → Prop}
124+
(mk : ∀ (x : X), motive (.mk x)) (x : ZerothHomotopy X) :
125+
motive x := by
126+
obtain ⟨x, rfl⟩ := mk_surjective x
127+
exact mk x
128+
129+
lemma sound {x y : X} (p : Path x y) : mk x = mk y :=
130+
Quotient.sound ⟨p⟩
131+
111132
/-- The quotient topology on path components. -/
112133
instance : TopologicalSpace <| ZerothHomotopy X :=
113134
inferInstanceAs <| TopologicalSpace <| Quotient _
114135

115-
instance ZerothHomotopy.inhabited : Inhabited (ZerothHomotopy ℝ) :=
136+
lemma isQuotientMap_mk : IsQuotientMap (ZerothHomotopy.mk (X := X)) :=
137+
isQuotientMap_quotient_mk'
138+
139+
instance inhabited : Inhabited (ZerothHomotopy ℝ) :=
116140
⟨@Quotient.mk' ℝ (pathSetoid ℝ) 0
117141

142+
section
143+
144+
variable {T : Type*} (f : X → T) (hf : ∀ ⦃x y : X⦄ (_ : Path x y), f x = f y)
145+
146+
/-- Constructor for maps from `ZerothHomotopy X`. -/
147+
def lift : ZerothHomotopy X → T :=
148+
Quotient.lift f fun _ _ ⟨p⟩ ↦ hf p
149+
150+
@[simp]
151+
lemma lift_mk (x : X) : lift f hf (.mk x) = f x := rfl
152+
153+
end
154+
155+
end ZerothHomotopy
156+
118157
variable {X}
119158

120159
/-! ### Being joined by a path inside a set -/
@@ -278,8 +317,8 @@ def ZerothHomotopy.toConnectedComponents : ZerothHomotopy X → ConnectedCompone
278317
Quotient.map id fun x _ h ↦ connectedComponent_eq <| pathComponent_subset_component x h
279318

280319
@[simp]
281-
theorem ZerothHomotopy.toConnectedComponents_apply (x : X) : toConnectedComponents ⟦x⟧ = ⟦x⟧ :=
282-
rfl
320+
theorem ZerothHomotopy.toConnectedComponents_apply (x : X) :
321+
toConnectedComponents (.mk x) = ⟦x⟧ := rfl
283322

284323
/-- There are at least as many path connected components as there are connected components -/
285324
theorem ZerothHomotopy.toConnectedComponents_surjective :
@@ -598,7 +637,7 @@ end PathConnectedSpace
598637
/-- The preimage of a singleton in `ZerothHomotopy` is the path component of an element in the
599638
equivalence class. -/
600639
theorem ZerothHomotopy.preimage_singleton_eq_pathComponent (x : X) :
601-
Quotient.mk' (s := pathSetoid X) ⁻¹' {⟦x⟧} = pathComponent x := by
640+
ZerothHomotopy.mk ⁻¹' {.mk x} = pathComponent x := by
602641
ext y
603642
rw [mem_preimage, mem_singleton_iff, eq_comm, mem_pathComponent_iff]
604643
exact Quotient.eq

0 commit comments

Comments
 (0)