l3lab/ntp-mathlib huggingface dataset:
/-- The `n+1`-dimensional loops are in bijection with the loops in the space of
  `n`-dimensional loops with base point `const`.
  We allow an arbitrary indexing type `N` in place of `Fin n` here. -/
@[simps]
def loopHomeo (i : N) : Ω^ N X x ≃ₜ Ω (Ω^ { j // j ≠ i } X x) const
    where
  toFun := toLoop i
  invFun := fromLoop i
  left_inv p := by ext; 

Proof state:
case H
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p : ↑(Ω^ N X x)
y✝ : N → ↑I
⊢ (fromLoop i (toLoop i p)) y✝ = p y✝

Next tactic:
exact congr_arg p (Equiv.apply_symm_apply _ _)
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  

Proof state:
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
⊢ Homotopic p q → Path.Homotopic (toLoop i p) (toLoop i q)

Next tactic:
refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · 

Proof state:
case refine'_1
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
⊢ (homotopyTo i H) t ∈ Ω^ { j // j ≠ i } X x

Next tactic:
rintro y ⟨i, iH⟩
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    

Proof state:
case refine'_1.intro
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ ((homotopyTo i✝ H) t) y = x

Next tactic:
rw [homotopyTo_apply, H.eq_fst, p.2]
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    

Proof state:
case refine'_1.intro.a
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ (Cube.insertAt i✝) (t.2, y) ∈ Cube.boundary N
case refine'_1.intro.hx
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ (Cube.insertAt i✝) (t.2, y) ∈ Cube.boundary N

Next tactic:
all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals 

Proof state:
case refine'_1.intro.a
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ (Cube.insertAt i✝) (t.2, y) ∈ Cube.boundary N

Next tactic:
apply Cube.insertAt_boundary
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; 

Proof state:
case refine'_1.intro.a.H
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ (t.2 = 0 ∨ t.2 = 1) ∨ y ∈ Cube.boundary { j // j ≠ i✝ }

Next tactic:
right
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; 

Proof state:
case refine'_1.intro.a.H.h
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ y ∈ Cube.boundary { j // j ≠ i✝ }

Next tactic:
exact ⟨i, iH⟩
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals 

Proof state:
case refine'_1.intro.hx
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ (Cube.insertAt i✝) (t.2, y) ∈ Cube.boundary N

Next tactic:
apply Cube.insertAt_boundary
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; 

Proof state:
case refine'_1.intro.hx.H
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ (t.2 = 0 ∨ t.2 = 1) ∨ y ∈ Cube.boundary { j // j ≠ i✝ }

Next tactic:
right
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; 

Proof state:
case refine'_1.intro.hx.H.h
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i✝ : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
t : ↑I × ↑I
y : { j // j ≠ i✝ } → ↑I
i : { j // j ≠ i✝ }
iH : y i = 0 ∨ y i = 1
⊢ y ∈ Cube.boundary { j // j ≠ i✝ }

Next tactic:
exact ⟨i, iH⟩
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · 

Proof state:
case refine'_2
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ Continuous fun t =>
    { val := (homotopyTo i H) t, property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) }

Next tactic:
continuity
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · continuity
  

Proof state:
case refine'_3
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (0, x_1) =
      (toLoop i p).toContinuousMap x_1
case refine'_4
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (1, x_1) =
      (toLoop i q).toContinuousMap x_1
case refine'_5
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (t x_1 : ↑I),
    x_1 ∈ {0, 1} →
      (ContinuousMap.mk fun x_2 =>
            ContinuousMap.toFun
              {
                  toContinuousMap :=
                    ContinuousMap.mk fun t =>
                      { val := (homotopyTo i H) t,
                        property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) },
                  map_zero_left := ?refine'_3, map_one_left := ?refine'_4 }.toContinuousMap
              (t, x_2))
          x_1 =
        (toLoop i p).toContinuousMap x_1

Next tactic:
iterate 2 intro; ext; erw [homotopyTo_apply, toLoop_apply]; swap
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · continuity
  iterate 2 

Proof state:
case refine'_3
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (0, x_1) =
      (toLoop i p).toContinuousMap x_1
case refine'_4
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (1, x_1) =
      (toLoop i q).toContinuousMap x_1
case refine'_5
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (t x_1 : ↑I),
    x_1 ∈ {0, 1} →
      (ContinuousMap.mk fun x_2 =>
            ContinuousMap.toFun
              {
                  toContinuousMap :=
                    ContinuousMap.mk fun t =>
                      { val := (homotopyTo i H) t,
                        property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) },
                  map_zero_left := ?refine'_3, map_one_left := ?refine'_4 }.toContinuousMap
              (t, x_2))
          x_1 =
        (toLoop i p).toContinuousMap x_1

Next tactic:
intro
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · continuity
  iterate 2 intro; 

Proof state:
case refine'_3
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
x✝ : ↑I
⊢ ContinuousMap.toFun
      (ContinuousMap.mk fun t =>
        { val := (homotopyTo i H) t, property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
      (0, x✝) =
    (toLoop i p).toContinuousMap x✝
case refine'_4
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (1, x_1) =
      (toLoop i q).toContinuousMap x_1
case refine'_5
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (t x_1 : ↑I),
    x_1 ∈ {0, 1} →
      (ContinuousMap.mk fun x_2 =>
            ContinuousMap.toFun
              {
                  toContinuousMap :=
                    ContinuousMap.mk fun t =>
                      { val := (homotopyTo i H) t,
                        property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) },
                  map_zero_left :=
                    (_ :
                      ∀ (x_3 : ↑I),
                        ContinuousMap.toFun
                            (ContinuousMap.mk fun t =>
                              { val := (homotopyTo i H) t,
                                property := (_ : (homotopyTo i H) t ∈ Ω^ { j // j ≠ i } X x) })
                            (0, x_3) =
                          (toLoop i p).toContinuousMap x_3),
                  map_one_left := ?refine'_4 }.toContinuousMap
              (t, x_2))
          x_1 =
        (toLoop i p).toContinuousMap x_1

Next tactic:
ext
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · continuity
  iterate 2 intro; ext; 

Proof state:
case refine'_3.H
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
x✝ : ↑I
y✝ : { j // j ≠ i } → ↑I
⊢ (ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (0, x✝))
      y✝ =
    ((toLoop i p).toContinuousMap x✝) y✝
case refine'_4
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (1, x_1) =
      (toLoop i q).toContinuousMap x_1
case refine'_5
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (t x_1 : ↑I),
    x_1 ∈ {0, 1} →
      (ContinuousMap.mk fun x_2 =>
            ContinuousMap.toFun
              {
                  toContinuousMap :=
                    ContinuousMap.mk fun t =>
                      { val := (homotopyTo i H) t,
                        property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) },
                  map_zero_left :=
                    (_ :
                      ∀ (x_3 : ↑I),
                        ContinuousMap.toFun
                            (ContinuousMap.mk fun t =>
                              { val := (homotopyTo i H) t,
                                property := (_ : (homotopyTo i H) t ∈ Ω^ { j // j ≠ i } X x) })
                            (0, x_3) =
                          (toLoop i p).toContinuousMap x_3),
                  map_one_left := ?refine'_4 }.toContinuousMap
              (t, x_2))
          x_1 =
        (toLoop i p).toContinuousMap x_1

Next tactic:
erw [homotopyTo_apply, toLoop_apply]
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · continuity
  iterate 2 intro; ext; erw [homotopyTo_apply, toLoop_apply]; 

Proof state:
case refine'_3.H
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
x✝ : ↑I
y✝ : { j // j ≠ i } → ↑I
⊢ H ((0, x✝).1, (Cube.insertAt i) ((0, x✝).2, y✝)) = p ((Cube.insertAt i) (x✝, y✝))
case refine'_4
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (1, x_1) =
      (toLoop i q).toContinuousMap x_1
case refine'_5
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (t x_1 : ↑I),
    x_1 ∈ {0, 1} →
      (ContinuousMap.mk fun x_2 =>
            ContinuousMap.toFun
              {
                  toContinuousMap :=
                    ContinuousMap.mk fun t =>
                      { val := (homotopyTo i H) t,
                        property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) },
                  map_zero_left :=
                    (_ :
                      ∀ (x_3 : ↑I),
                        ContinuousMap.toFun
                            (ContinuousMap.mk fun t =>
                              { val := (homotopyTo i H) t,
                                property := (_ : (homotopyTo i H) t ∈ Ω^ { j // j ≠ i } X x) })
                            (0, x_3) =
                          (toLoop i p).toContinuousMap x_3),
                  map_one_left := ?refine'_4 }.toContinuousMap
              (t, x_2))
          x_1 =
        (toLoop i p).toContinuousMap x_1

Next tactic:
swap
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · continuity
  iterate 2 

Proof state:
case refine'_4
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (x_1 : ↑I),
    ContinuousMap.toFun
        (ContinuousMap.mk fun t =>
          { val := (homotopyTo i H) t,
            property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
        (1, x_1) =
      (toLoop i q).toContinuousMap x_1
case refine'_3.H
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
x✝ : ↑I
y✝ : { j // j ≠ i } → ↑I
⊢ H ((0, x✝).1, (Cube.insertAt i) ((0, x✝).2, y✝)) = p ((Cube.insertAt i) (x✝, y✝))
case refine'_5
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (t x_1 : ↑I),
    x_1 ∈ {0, 1} →
      (ContinuousMap.mk fun x_2 =>
            ContinuousMap.toFun
              {
                  toContinuousMap :=
                    ContinuousMap.mk fun t =>
                      { val := (homotopyTo i H) t,
                        property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) },
                  map_zero_left :=
                    (_ :
                      ∀ (x_3 : ↑I),
                        ContinuousMap.toFun
                            (ContinuousMap.mk fun t =>
                              { val := (homotopyTo i H) t,
                                property := (_ : (homotopyTo i H) t ∈ Ω^ { j // j ≠ i } X x) })
                            (0, x_3) =
                          (toLoop i p).toContinuousMap x_3),
                  map_one_left := ?refine'_4 }.toContinuousMap
              (t, x_2))
          x_1 =
        (toLoop i p).toContinuousMap x_1

Next tactic:
intro
theorem homotopicTo (i : N) {p q : Ω^ N X x} :
    Homotopic p q → (toLoop i p).Homotopic (toLoop i q) := by
  refine' Nonempty.map fun H => ⟨⟨⟨fun t => ⟨homotopyTo i H t, _⟩, _⟩, _, _⟩, _⟩
  · rintro y ⟨i, iH⟩
    rw [homotopyTo_apply, H.eq_fst, p.2]
    all_goals apply Cube.insertAt_boundary; right; exact ⟨i, iH⟩
  · continuity
  iterate 2 intro; 

Proof state:
case refine'_4
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
x✝ : ↑I
⊢ ContinuousMap.toFun
      (ContinuousMap.mk fun t =>
        { val := (homotopyTo i H) t, property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) })
      (1, x✝) =
    (toLoop i q).toContinuousMap x✝
case refine'_3.H
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
x✝ : ↑I
y✝ : { j // j ≠ i } → ↑I
⊢ H ((0, x✝).1, (Cube.insertAt i) ((0, x✝).2, y✝)) = p ((Cube.insertAt i) (x✝, y✝))
case refine'_5
N : Type u_1
X : Type u_2
inst✝¹ : TopologicalSpace X
x : X
inst✝ : DecidableEq N
i : N
p q : ↑(Ω^ N X x)
H : ContinuousMap.HomotopyRel (↑p) (↑q) (Cube.boundary N)
⊢ ∀ (t x_1 : ↑I),
    x_1 ∈ {0, 1} →
      (ContinuousMap.mk fun x_2 =>
            ContinuousMap.toFun
              {
                  toContinuousMap :=
                    ContinuousMap.mk fun t =>
                      { val := (homotopyTo i H) t,
                        property := (_ : ∀ y ∈ Cube.boundary { j // j ≠ i }, ((homotopyTo i H) t) y = x) },
                  map_zero_left :=
                    (_ :
                      ∀ (x_3 : ↑I),
                        ContinuousMap.toFun
                            (ContinuousMap.mk fun t =>
                              { val := (homotopyTo i H) t,
                                property := (_ : (homotopyTo i H) t ∈ Ω^ { j // j ≠ i } X x) })
                            (0, x_3) =
                          (toLoop i p).toContinuousMap x_3),
                  map_one_left :=
                    (_ :
                      ∀ (x_3 : ↑I),
                        ContinuousMap.toFun
                            (ContinuousMap.mk fun t =>
                              { val := (homotopyTo i H) t,
                                property := (_ : (homotopyTo i H) t ∈ Ω^ { j // j ≠ i } X x) })
                            (1, x_3) =
                          (toLoop i q).toContinuousMap x_3) }.toContinuousMap
              (t, x_2))
          x_1 =
        (toLoop i p).toContinuousMap x_1

Next tactic:
ext