Theorem: nonempty_sections_of_finite_cofiltered_system
File: Mathlib/CategoryTheory/CofilteredSystem.lean

tactic: let J' : Type max w v u := AsSmall.{max w v} J
state_before: J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
⊢ Set.Nonempty (Functor.sections F)

tactic: let down : J' ⥤ J := AsSmall.down
state_before: J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
⊢ Set.Nonempty (Functor.sections F)

tactic: let F' : J' ⥤ Type max u v w := down ⋙ F ⋙ uliftFunctor.{max u w, v}
state_before: J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
⊢ Set.Nonempty (Functor.sections F)

tactic: haveI : ∀ i, Nonempty (F'.obj i) := fun i => ⟨⟨Classical.arbitrary (F.obj (down.obj i))⟩⟩
state_before: J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
⊢ Set.Nonempty (Functor.sections F)

tactic: haveI : ∀ i, Finite (F'.obj i) := fun i => Finite.of_equiv (F.obj (down.obj i)) Equiv.ulift.symm
state_before: J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this : ∀ (i : J'), _root_.Nonempty (F'.obj i)
⊢ Set.Nonempty (Functor.sections F)

tactic: cases isEmpty_or_nonempty J
state_before: J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this : ∀ (i : J'), Finite (F'.obj i)
⊢ Set.Nonempty (Functor.sections F)

tactic: haveI : IsCofiltered J := ⟨⟩
state_before: case inr
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this : ∀ (i : J'), Finite (F'.obj i)
h✝ : _root_.Nonempty J
⊢ Set.Nonempty (Functor.sections F)

tactic: obtain ⟨u, hu⟩ := nonempty_sections_of_finite_cofiltered_system.init F'
state_before: case inr
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝¹ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this✝ : ∀ (i : J'), Finite (F'.obj i)
h✝ : _root_.Nonempty J
this : IsCofiltered J
⊢ Set.Nonempty (Functor.sections F)

tactic: use fun j => (u ⟨j⟩).down
state_before: case inr.intro
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝¹ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this✝ : ∀ (i : J'), Finite (F'.obj i)
h✝ : _root_.Nonempty J
this : IsCofiltered J
u : (j : J') → F'.obj j
hu : u ∈ Functor.sections F'
⊢ Set.Nonempty (Functor.sections F)

tactic: intro j j' f
state_before: case inr.intro
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝¹ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this✝ : ∀ (i : J'), Finite (F'.obj i)
h✝ : _root_.Nonempty J
this : IsCofiltered J
u : (j : J') → F'.obj j
hu : u ∈ Functor.sections F'
⊢ (fun j => (u { down := j }).down) ∈ Functor.sections F

tactic: have h := @hu (⟨j⟩ : J') (⟨j'⟩ : J') (ULift.up f)
state_before: case inr.intro
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝¹ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this✝ : ∀ (i : J'), Finite (F'.obj i)
h✝ : _root_.Nonempty J
this : IsCofiltered J
u : (j : J') → F'.obj j
hu : u ∈ Functor.sections F'
j j' : J
f : j ⟶ j'
⊢ F.map f ((fun j => (u { down := j }).down) j) = (fun j => (u { down := j }).down) j'

tactic: simp only [AsSmall.down, Functor.comp_map, uliftFunctor_map, Functor.op_map] at h
state_before: case inr.intro
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝¹ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this✝ : ∀ (i : J'), Finite (F'.obj i)
h✝ : _root_.Nonempty J
this : IsCofiltered J
u : (j : J') → F'.obj j
hu : u ∈ Functor.sections F'
j j' : J
f : j ⟶ j'
h : F'.map { down := f } (u { down := j }) = u { down := j' }
⊢ F.map f ((fun j => (u { down := j }).down) j) = (fun j => (u { down := j }).down) j'

tactic: simp_rw [← h]
state_before: case inr.intro
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝¹ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this✝ : ∀ (i : J'), Finite (F'.obj i)
h✝ : _root_.Nonempty J
this : IsCofiltered J
u : (j : J') → F'.obj j
hu : u ∈ Functor.sections F'
j j' : J
f : j ⟶ j'
h : { down := F.map f (u { down := j }).down } = u { down := j' }
⊢ F.map f ((fun j => (u { down := j }).down) j) = (fun j => (u { down := j }).down) j'

tactic: fconstructor <;> apply isEmptyElim
state_before: case inl
J : Type u
inst✝³ : Category J
inst✝² : IsCofilteredOrEmpty J
F : J ⥤ Type v
inst✝¹ : ∀ (j : J), Finite (F.obj j)
inst✝ : ∀ (j : J), _root_.Nonempty (F.obj j)
J' : Type (max w v u) := AsSmall J
down : J' ⥤ J := AsSmall.down
F' : J' ⥤ Type (max u v w) := down ⋙ F ⋙ uliftFunctor
this✝ : ∀ (i : J'), _root_.Nonempty (F'.obj i)
this : ∀ (i : J'), Finite (F'.obj i)
h✝ : IsEmpty J
⊢ Set.Nonempty (Functor.sections F)