[GOAL]
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Monoid G
n : ℕ
A : Rep k G
f g : (Fin n → G) → CoeSort.coe A
⊢ (fun f g =>
        ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
          Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
      (f + g) =
    (fun f g =>
          ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
            Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
        f +
      (fun f g =>
          ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
            Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
        g
[PROOFSTEP]
ext x
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Monoid G
n : ℕ
A : Rep k G
f g : (Fin n → G) → CoeSort.coe A
x : Fin (n + 1) → G
⊢ (fun f g =>
        ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
          Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
      (f + g) x =
    ((fun f g =>
            ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
              Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
          f +
        (fun f g =>
            ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
              Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
          g)
      x
[PROOFSTEP]
simp_rw [Pi.add_apply, map_add, smul_add, Finset.sum_add_distrib, add_add_add_comm]
[GOAL]
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Monoid G
n : ℕ
A : Rep k G
r : k
f : (Fin n → G) → CoeSort.coe A
⊢ AddHom.toFun
      {
        toFun := fun f g =>
          ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
            Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g),
        map_add' :=
          (_ :
            ∀ (f g : (Fin n → G) → CoeSort.coe A),
              (fun f g =>
                    ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                      Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                  (f + g) =
                (fun f g =>
                      ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                        Finset.sum Finset.univ fun j =>
                          (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                    f +
                  (fun f g =>
                      ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                        Finset.sum Finset.univ fun j =>
                          (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                    g) }
      (r • f) =
    ↑(RingHom.id k) r •
      AddHom.toFun
        {
          toFun := fun f g =>
            ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
              Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g),
          map_add' :=
            (_ :
              ∀ (f g : (Fin n → G) → CoeSort.coe A),
                (fun f g =>
                      ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                        Finset.sum Finset.univ fun j =>
                          (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                    (f + g) =
                  (fun f g =>
                        ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                          Finset.sum Finset.univ fun j =>
                            (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                      f +
                    (fun f g =>
                        ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                          Finset.sum Finset.univ fun j =>
                            (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                      g) }
        f
[PROOFSTEP]
ext x
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Monoid G
n : ℕ
A : Rep k G
r : k
f : (Fin n → G) → CoeSort.coe A
x : Fin (n + 1) → G
⊢ AddHom.toFun
      {
        toFun := fun f g =>
          ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
            Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g),
        map_add' :=
          (_ :
            ∀ (f g : (Fin n → G) → CoeSort.coe A),
              (fun f g =>
                    ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                      Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                  (f + g) =
                (fun f g =>
                      ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                        Finset.sum Finset.univ fun j =>
                          (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                    f +
                  (fun f g =>
                      ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                        Finset.sum Finset.univ fun j =>
                          (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                    g) }
      (r • f) x =
    (↑(RingHom.id k) r •
        AddHom.toFun
          {
            toFun := fun f g =>
              ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g),
            map_add' :=
              (_ :
                ∀ (f g : (Fin n → G) → CoeSort.coe A),
                  (fun f g =>
                        ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                          Finset.sum Finset.univ fun j =>
                            (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                      (f + g) =
                    (fun f g =>
                          ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                            Finset.sum Finset.univ fun j =>
                              (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                        f +
                      (fun f g =>
                          ↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
                            Finset.sum Finset.univ fun j =>
                              (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g))
                        g) }
          f)
      x
[PROOFSTEP]
simp_rw [Pi.smul_apply, RingHom.id_apply, map_smul, smul_add, Finset.smul_sum, ← smul_assoc, smul_eq_mul, mul_comm r]
[GOAL]
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
⊢ d n A =
    (LinearEquiv.toModuleIso (diagonalHomEquiv n A)).inv ≫
      HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1) ≫
        (LinearEquiv.toModuleIso (diagonalHomEquiv (n + 1) A)).hom
[PROOFSTEP]
ext f g
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ ↑(d n A) f g =
    ↑((LinearEquiv.toModuleIso (diagonalHomEquiv n A)).inv ≫
          HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1) ≫
            (LinearEquiv.toModuleIso (diagonalHomEquiv (n + 1) A)).hom)
      f g
[PROOFSTEP]
change d n A f g = diagonalHomEquiv (n + 1) A ((resolution k G).d (n + 1) n ≫ (diagonalHomEquiv n A).symm f) g
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ ↑(d n A) f g =
    ↑(diagonalHomEquiv (n + 1) A)
      (HomologicalComplex.d (resolution k G) (n + 1) n ≫ ↑(LinearEquiv.symm (diagonalHomEquiv n A)) f) g
[PROOFSTEP]
rw [diagonalHomEquiv_apply, Action.comp_hom, ModuleCat.comp_def, LinearMap.comp_apply, Resolution.d_eq]
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ ↑(d n A) f g =
    ↑(↑(LinearEquiv.symm (diagonalHomEquiv n A)) f).hom
      (↑(Resolution.d k G (n + 1)) (Finsupp.single (Fin.partialProd g) 1))
[PROOFSTEP]
erw [Resolution.d_of (Fin.partialProd g)]
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ ↑(d n A) f g =
    ↑(↑(LinearEquiv.symm (diagonalHomEquiv n A)) f).hom
      (Finset.sum Finset.univ fun p => Finsupp.single (Fin.partialProd g ∘ Fin.succAbove p) ((-1) ^ ↑p))
[PROOFSTEP]
rw [LinearMap.map_sum]
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ ↑(d n A) f g =
    Finset.sum Finset.univ fun i =>
      ↑(↑(LinearEquiv.symm (diagonalHomEquiv n A)) f).hom
        (Finsupp.single (Fin.partialProd g ∘ Fin.succAbove i) ((-1) ^ ↑i))
[PROOFSTEP]
simp only [← Finsupp.smul_single_one _ ((-1 : k) ^ _)]
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ ↑(d n A) f g =
    Finset.sum Finset.univ fun x =>
      ↑(↑(LinearEquiv.symm (diagonalHomEquiv n A)) f).hom
        ((-1) ^ ↑x • Finsupp.single (Fin.partialProd g ∘ Fin.succAbove x) 1)
[PROOFSTEP]
rw [d_apply, @Fin.sum_univ_succ _ _ (n + 1), Fin.val_zero, pow_zero, one_smul, Fin.succAbove_zero,
  diagonalHomEquiv_symm_apply f (Fin.partialProd g ∘ @Fin.succ (n + 1))]
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ (↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
      Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g)) =
    ↑(↑(ρ A) ((Fin.partialProd g ∘ Fin.succ) 0))
        (f fun i => ((Fin.partialProd g ∘ Fin.succ) (Fin.castSucc i))⁻¹ * (Fin.partialProd g ∘ Fin.succ) (Fin.succ i)) +
      Finset.sum Finset.univ fun i =>
        ↑(↑(LinearEquiv.symm (diagonalHomEquiv n A)) f).hom
          ((-1) ^ ↑(Fin.succ i) • Finsupp.single (Fin.partialProd g ∘ Fin.succAbove (Fin.succ i)) 1)
[PROOFSTEP]
simp_rw [Function.comp_apply, Fin.partialProd_succ, Fin.castSucc_zero, Fin.partialProd_zero, one_mul]
[GOAL]
case h.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
⊢ (↑(↑(ρ A) (g 0)) (f fun i => g (Fin.succ i)) +
      Finset.sum Finset.univ fun j => (-1) ^ (↑j + 1) • f (Fin.contractNth j (fun x x_1 => x * x_1) g)) =
    ↑(↑(ρ A) (g 0))
        (f fun i =>
          (Fin.partialProd g (Fin.castSucc (Fin.castSucc i)) * g (Fin.castSucc i))⁻¹ *
            (Fin.partialProd g (Fin.castSucc (Fin.succ i)) * g (Fin.succ i))) +
      Finset.sum Finset.univ fun i =>
        ↑(↑(LinearEquiv.symm (diagonalHomEquiv n A)) f).hom
          ((-1) ^ ↑(Fin.succ i) • Finsupp.single (Fin.partialProd g ∘ Fin.succAbove (Fin.succ i)) 1)
[PROOFSTEP]
rcongr x
[GOAL]
case h.h.e_a.h.e_6.h.e_a.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
x : Fin n
⊢ g (Fin.succ x) =
    (Fin.partialProd g (Fin.castSucc (Fin.castSucc x)) * g (Fin.castSucc x))⁻¹ *
      (Fin.partialProd g (Fin.castSucc (Fin.succ x)) * g (Fin.succ x))
[PROOFSTEP]
have := Fin.partialProd_right_inv g (Fin.castSucc x)
[GOAL]
case h.h.e_a.h.e_6.h.e_a.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
x : Fin n
this :
  (Fin.partialProd g (Fin.castSucc (Fin.castSucc x)))⁻¹ * Fin.partialProd g (Fin.succ (Fin.castSucc x)) =
    g (Fin.castSucc x)
⊢ g (Fin.succ x) =
    (Fin.partialProd g (Fin.castSucc (Fin.castSucc x)) * g (Fin.castSucc x))⁻¹ *
      (Fin.partialProd g (Fin.castSucc (Fin.succ x)) * g (Fin.succ x))
[PROOFSTEP]
simp only [mul_inv_rev, Fin.castSucc_fin_succ] at this ⊢
[GOAL]
case h.h.e_a.h.e_6.h.e_a.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
x : Fin n
this :
  (Fin.partialProd g (Fin.castSucc (Fin.castSucc x)))⁻¹ * Fin.partialProd g (Fin.succ (Fin.castSucc x)) =
    g (Fin.castSucc x)
⊢ g (Fin.succ x) =
    (g (Fin.castSucc x))⁻¹ * (Fin.partialProd g (Fin.castSucc (Fin.castSucc x)))⁻¹ *
      (Fin.partialProd g (Fin.succ (Fin.castSucc x)) * g (Fin.succ x))
[PROOFSTEP]
rw [mul_assoc, ← mul_assoc _ _ (g x.succ), this, inv_mul_cancel_left]
[GOAL]
case h.h.e_a.e_f.h
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
f : (Fin n → G) → CoeSort.coe A
g : Fin (n + 1) → G
x : Fin (n + 1)
⊢ (-1) ^ (↑x + 1) • f (Fin.contractNth x (fun x x_1 => x * x_1) g) =
    ↑(↑(LinearEquiv.symm (diagonalHomEquiv n A)) f).hom
      ((-1) ^ ↑(Fin.succ x) • Finsupp.single (Fin.partialProd g ∘ Fin.succAbove (Fin.succ x)) 1)
[PROOFSTEP]
rw [map_smul, diagonalHomEquiv_symm_partialProd_succ, Fin.val_succ]
[GOAL]
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Group G
A : Rep k G
n : ℕ
⊢ (fun n => d n A) n ≫ (fun n => d n A) (n + 1) = 0
[PROOFSTEP]
ext x
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Group G
A : Rep k G
n : ℕ
x : ↑((fun n => ModuleCat.of k ((Fin n → G) → CoeSort.coe A)) n)
⊢ ↑((fun n => d n A) n ≫ (fun n => d n A) (n + 1)) x = ↑0 x
[PROOFSTEP]
have := LinearMap.ext_iff.1 ((linearYonedaObjResolution A).d_comp_d n (n + 1) (n + 2))
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Group G
A : Rep k G
n : ℕ
x : ↑((fun n => ModuleCat.of k ((Fin n → G) → CoeSort.coe A)) n)
this :
  ∀ (x : ↑(HomologicalComplex.X (linearYonedaObjResolution A) n)),
    ↑(HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1) ≫
            HomologicalComplex.d (linearYonedaObjResolution A) (n + 1) (n + 2))
        x =
      ↑0 x
⊢ ↑((fun n => d n A) n ≫ (fun n => d n A) (n + 1)) x = ↑0 x
[PROOFSTEP]
simp only [ModuleCat.comp_def, LinearMap.comp_apply] at this
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Group G
A : Rep k G
n : ℕ
x : ↑((fun n => ModuleCat.of k ((Fin n → G) → CoeSort.coe A)) n)
this :
  ∀ (x : ↑(HomologicalComplex.X (linearYonedaObjResolution A) n)),
    ↑(HomologicalComplex.d (linearYonedaObjResolution A) (n + 1) (n + 2))
        (↑(HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1)) x) =
      ↑0 x
⊢ ↑((fun n => d n A) n ≫ (fun n => d n A) (n + 1)) x = ↑0 x
[PROOFSTEP]
dsimp only
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Group G
A : Rep k G
n : ℕ
x : ↑((fun n => ModuleCat.of k ((Fin n → G) → CoeSort.coe A)) n)
this :
  ∀ (x : ↑(HomologicalComplex.X (linearYonedaObjResolution A) n)),
    ↑(HomologicalComplex.d (linearYonedaObjResolution A) (n + 1) (n + 2))
        (↑(HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1)) x) =
      ↑0 x
⊢ ↑(d n A ≫ d (n + 1) A) x = ↑0 x
[PROOFSTEP]
simp only [d_eq, LinearEquiv.toModuleIso_inv, LinearEquiv.toModuleIso_hom, ModuleCat.coe_comp, Function.comp_apply]
  /- Porting note: I can see I need to rewrite `LinearEquiv.coe_coe` twice to at
        least reduce the need for `symm_apply_apply` to be an `erw`. However, even `erw` refuses to
        rewrite the second `coe_coe`... -/
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Group G
A : Rep k G
n : ℕ
x : ↑((fun n => ModuleCat.of k ((Fin n → G) → CoeSort.coe A)) n)
this :
  ∀ (x : ↑(HomologicalComplex.X (linearYonedaObjResolution A) n)),
    ↑(HomologicalComplex.d (linearYonedaObjResolution A) (n + 1) (n + 2))
        (↑(HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1)) x) =
      ↑0 x
⊢ ↑↑(Rep.diagonalHomEquiv (n + 1 + 1) A)
      (↑(HomologicalComplex.d (linearYonedaObjResolution A) (n + 1) (n + 1 + 1))
        (↑↑(LinearEquiv.symm (Rep.diagonalHomEquiv (n + 1) A))
          (↑↑(Rep.diagonalHomEquiv (n + 1) A)
            (↑(HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1))
              (↑↑(LinearEquiv.symm (Rep.diagonalHomEquiv n A)) x))))) =
    ↑0 x
[PROOFSTEP]
erw [LinearEquiv.symm_apply_apply, this]
[GOAL]
case h
k G : Type u
inst✝¹ : CommRing k
n✝ : ℕ
inst✝ : Group G
A : Rep k G
n : ℕ
x : ↑((fun n => ModuleCat.of k ((Fin n → G) → CoeSort.coe A)) n)
this :
  ∀ (x : ↑(HomologicalComplex.X (linearYonedaObjResolution A) n)),
    ↑(HomologicalComplex.d (linearYonedaObjResolution A) (n + 1) (n + 2))
        (↑(HomologicalComplex.d (linearYonedaObjResolution A) n (n + 1)) x) =
      ↑0 x
⊢ ↑↑(Rep.diagonalHomEquiv (n + 1 + 1) A) (↑0 (↑↑(LinearEquiv.symm (Rep.diagonalHomEquiv n A)) x)) = ↑0 x
[PROOFSTEP]
exact map_zero _
[GOAL]
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
⊢ inhomogeneousCochains A ≅ linearYonedaObjResolution A
[PROOFSTEP]
refine' HomologicalComplex.Hom.isoOfComponents (fun i => (Rep.diagonalHomEquiv i A).toModuleIso.symm) _
[GOAL]
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
⊢ ∀ (i j : ℕ),
    ComplexShape.Rel (ComplexShape.up ℕ) i j →
      ((fun i => (LinearEquiv.toModuleIso (Rep.diagonalHomEquiv i A)).symm) i).hom ≫
          HomologicalComplex.d (linearYonedaObjResolution A) i j =
        HomologicalComplex.d (inhomogeneousCochains A) i j ≫
          ((fun i => (LinearEquiv.toModuleIso (Rep.diagonalHomEquiv i A)).symm) j).hom
[PROOFSTEP]
rintro i j (h : i + 1 = j)
[GOAL]
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
i j : ℕ
h : i + 1 = j
⊢ ((fun i => (LinearEquiv.toModuleIso (Rep.diagonalHomEquiv i A)).symm) i).hom ≫
      HomologicalComplex.d (linearYonedaObjResolution A) i j =
    HomologicalComplex.d (inhomogeneousCochains A) i j ≫
      ((fun i => (LinearEquiv.toModuleIso (Rep.diagonalHomEquiv i A)).symm) j).hom
[PROOFSTEP]
subst h
[GOAL]
k G : Type u
inst✝¹ : CommRing k
n : ℕ
inst✝ : Group G
A : Rep k G
i : ℕ
⊢ ((fun i => (LinearEquiv.toModuleIso (Rep.diagonalHomEquiv i A)).symm) i).hom ≫
      HomologicalComplex.d (linearYonedaObjResolution A) i (i + 1) =
    HomologicalComplex.d (inhomogeneousCochains A) i (i + 1) ≫
      ((fun i => (LinearEquiv.toModuleIso (Rep.diagonalHomEquiv i A)).symm) (i + 1)).hom
[PROOFSTEP]
simp only [CochainComplex.of_d, d_eq, Category.assoc, Iso.symm_hom, Iso.hom_inv_id, Category.comp_id]


[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' ι'' : Finset ι
h : ι' ⊆ ι''
f : ↑(hallMatchingsOn t ι'')
⊢ ↑(hallMatchingsOn t ι')
[PROOFSTEP]
refine' ⟨fun i => f.val ⟨i, h i.property⟩, _⟩
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' ι'' : Finset ι
h : ι' ⊆ ι''
f : ↑(hallMatchingsOn t ι'')
⊢ (fun i => ↑f { val := ↑i, property := (_ : ↑i ∈ ι'') }) ∈ hallMatchingsOn t ι'
[PROOFSTEP]
cases' f.property with hinj hc
[GOAL]
case intro
ι : Type u
α : Type v
t : ι → Finset α
ι' ι'' : Finset ι
h : ι' ⊆ ι''
f : ↑(hallMatchingsOn t ι'')
hinj : Function.Injective ↑f
hc : ∀ (x : { x // x ∈ ι'' }), ↑f x ∈ t ↑x
⊢ (fun i => ↑f { val := ↑i, property := (_ : ↑i ∈ ι'') }) ∈ hallMatchingsOn t ι'
[PROOFSTEP]
refine' ⟨_, fun i => hc ⟨i, h i.property⟩⟩
[GOAL]
case intro
ι : Type u
α : Type v
t : ι → Finset α
ι' ι'' : Finset ι
h : ι' ⊆ ι''
f : ↑(hallMatchingsOn t ι'')
hinj : Function.Injective ↑f
hc : ∀ (x : { x // x ∈ ι'' }), ↑f x ∈ t ↑x
⊢ Function.Injective fun i => ↑f { val := ↑i, property := (_ : ↑i ∈ ι'') }
[PROOFSTEP]
rintro ⟨i, hi⟩ ⟨j, hj⟩ hh
[GOAL]
case intro.mk.mk
ι : Type u
α : Type v
t : ι → Finset α
ι' ι'' : Finset ι
h : ι' ⊆ ι''
f : ↑(hallMatchingsOn t ι'')
hinj : Function.Injective ↑f
hc : ∀ (x : { x // x ∈ ι'' }), ↑f x ∈ t ↑x
i : ι
hi : i ∈ ι'
j : ι
hj : j ∈ ι'
hh :
  (fun i => ↑f { val := ↑i, property := (_ : ↑i ∈ ι'') }) { val := i, property := hi } =
    (fun i => ↑f { val := ↑i, property := (_ : ↑i ∈ ι'') }) { val := j, property := hj }
⊢ { val := i, property := hi } = { val := j, property := hj }
[PROOFSTEP]
simpa only [Subtype.mk_eq_mk] using hinj hh
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
⊢ Nonempty ↑(hallMatchingsOn t ι')
[PROOFSTEP]
classical
refine' ⟨Classical.indefiniteDescription _ _⟩
apply (all_card_le_biUnion_card_iff_existsInjective' fun i : ι' => t i).mp
intro s'
convert h (s'.image (↑)) using 1
simp only [card_image_of_injective s' Subtype.coe_injective]
rw [image_biUnion]
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
⊢ Nonempty ↑(hallMatchingsOn t ι')
[PROOFSTEP]
refine' ⟨Classical.indefiniteDescription _ _⟩
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
⊢ ∃ x, x ∈ hallMatchingsOn t ι'
[PROOFSTEP]
apply (all_card_le_biUnion_card_iff_existsInjective' fun i : ι' => t i).mp
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
⊢ ∀ (s : Finset { x // x ∈ ι' }), card s ≤ card (Finset.biUnion s fun i => t ↑i)
[PROOFSTEP]
intro s'
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
s' : Finset { x // x ∈ ι' }
⊢ card s' ≤ card (Finset.biUnion s' fun i => t ↑i)
[PROOFSTEP]
convert h (s'.image (↑)) using 1
[GOAL]
case h.e'_3
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
s' : Finset { x // x ∈ ι' }
⊢ card s' = card (image Subtype.val s')
case h.e'_4
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
s' : Finset { x // x ∈ ι' }
⊢ card (Finset.biUnion s' fun i => t ↑i) = card (Finset.biUnion (image Subtype.val s') t)
[PROOFSTEP]
simp only [card_image_of_injective s' Subtype.coe_injective]
[GOAL]
case h.e'_4
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
ι' : Finset ι
s' : Finset { x // x ∈ ι' }
⊢ card (Finset.biUnion s' fun i => t ↑i) = card (Finset.biUnion (image Subtype.val s') t)
[PROOFSTEP]
rw [image_biUnion]
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
⊢ Finite ↑(hallMatchingsOn t ι')
[PROOFSTEP]
classical
rw [hallMatchingsOn]
let g : hallMatchingsOn t ι' → ι' → ι'.biUnion t := by
  rintro f i
  refine' ⟨f.val i, _⟩
  rw [mem_biUnion]
  exact ⟨i, i.property, f.property.2 i⟩
apply Finite.of_injective g
intro f f' h
ext a
rw [Function.funext_iff] at h
simpa using h a
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
⊢ Finite ↑(hallMatchingsOn t ι')
[PROOFSTEP]
rw [hallMatchingsOn]
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
⊢ Finite ↑{f | Function.Injective f ∧ ∀ (x : { x // x ∈ ι' }), f x ∈ t ↑x}
[PROOFSTEP]
let g : hallMatchingsOn t ι' → ι' → ι'.biUnion t := by
  rintro f i
  refine' ⟨f.val i, _⟩
  rw [mem_biUnion]
  exact ⟨i, i.property, f.property.2 i⟩
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
⊢ ↑(hallMatchingsOn t ι') → { x // x ∈ ι' } → { x // x ∈ Finset.biUnion ι' t }
[PROOFSTEP]
rintro f i
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
f : ↑(hallMatchingsOn t ι')
i : { x // x ∈ ι' }
⊢ { x // x ∈ Finset.biUnion ι' t }
[PROOFSTEP]
refine' ⟨f.val i, _⟩
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
f : ↑(hallMatchingsOn t ι')
i : { x // x ∈ ι' }
⊢ ↑f i ∈ Finset.biUnion ι' t
[PROOFSTEP]
rw [mem_biUnion]
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
f : ↑(hallMatchingsOn t ι')
i : { x // x ∈ ι' }
⊢ ∃ a, a ∈ ι' ∧ ↑f i ∈ t a
[PROOFSTEP]
exact ⟨i, i.property, f.property.2 i⟩
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
g : ↑(hallMatchingsOn t ι') → { x // x ∈ ι' } → { x // x ∈ Finset.biUnion ι' t } :=
  fun f i => { val := ↑f i, property := (_ : ↑f i ∈ Finset.biUnion ι' t) }
⊢ Finite ↑{f | Function.Injective f ∧ ∀ (x : { x // x ∈ ι' }), f x ∈ t ↑x}
[PROOFSTEP]
apply Finite.of_injective g
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
g : ↑(hallMatchingsOn t ι') → { x // x ∈ ι' } → { x // x ∈ Finset.biUnion ι' t } :=
  fun f i => { val := ↑f i, property := (_ : ↑f i ∈ Finset.biUnion ι' t) }
⊢ Function.Injective g
[PROOFSTEP]
intro f f' h
[GOAL]
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
g : ↑(hallMatchingsOn t ι') → { x // x ∈ ι' } → { x // x ∈ Finset.biUnion ι' t } :=
  fun f i => { val := ↑f i, property := (_ : ↑f i ∈ Finset.biUnion ι' t) }
f f' : ↑(hallMatchingsOn t ι')
h : g f = g f'
⊢ f = f'
[PROOFSTEP]
ext a
[GOAL]
case a.h
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
g : ↑(hallMatchingsOn t ι') → { x // x ∈ ι' } → { x // x ∈ Finset.biUnion ι' t } :=
  fun f i => { val := ↑f i, property := (_ : ↑f i ∈ Finset.biUnion ι' t) }
f f' : ↑(hallMatchingsOn t ι')
h : g f = g f'
a : { x // x ∈ ι' }
⊢ ↑f a = ↑f' a
[PROOFSTEP]
rw [Function.funext_iff] at h
[GOAL]
case a.h
ι : Type u
α : Type v
t : ι → Finset α
ι' : Finset ι
g : ↑(hallMatchingsOn t ι') → { x // x ∈ ι' } → { x // x ∈ Finset.biUnion ι' t } :=
  fun f i => { val := ↑f i, property := (_ : ↑f i ∈ Finset.biUnion ι' t) }
f f' : ↑(hallMatchingsOn t ι')
h : ∀ (a : { x // x ∈ ι' }), g f a = g f' a
a : { x // x ∈ ι' }
⊢ ↑f a = ↑f' a
[PROOFSTEP]
simpa using h a
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
⊢ (∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)) ↔ ∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x
[PROOFSTEP]
constructor
[GOAL]
case mp
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
⊢ (∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)) → ∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x
[PROOFSTEP]
intro h
[GOAL]
case mp
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
⊢ ∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x
[PROOFSTEP]
haveI : ∀ ι' : (Finset ι)ᵒᵖ, Nonempty ((hallMatchingsFunctor t).obj ι') := fun ι' =>
  hallMatchingsOn.nonempty t h ι'.unop
[GOAL]
case mp
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
⊢ ∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x
[PROOFSTEP]
classical
haveI : ∀ ι' : (Finset ι)ᵒᵖ, Finite ((hallMatchingsFunctor t).obj ι') :=
  by
  intro ι'
  rw [hallMatchingsFunctor]
  infer_instance
    -- Apply the compactness argument
obtain ⟨u, hu⟩ :=
  nonempty_sections_of_finite_inverse_system
    (hallMatchingsFunctor t)
      -- Interpret the resulting section of the inverse limit
refine' ⟨_, _, _⟩
·
  -- Build the matching function from the sectionexact fun i =>
    (u (Opposite.op ({ i } : Finset ι))).val ⟨i, by simp only [Opposite.unop_op, mem_singleton]⟩
·
  -- Show that it is injective
  intro i i'
  have subi : ({ i } : Finset ι) ⊆ { i, i' } := by simp
  have subi' : ({ i' } : Finset ι) ⊆ { i, i' } := by simp
  rw [← Finset.le_iff_subset] at subi subi'
  simp only
  rw [← hu (CategoryTheory.homOfLE subi).op, ← hu (CategoryTheory.homOfLE subi').op]
  let uii' := u (Opposite.op ({ i, i' } : Finset ι))
  exact fun h => Subtype.mk_eq_mk.mp (uii'.property.1 h)
·
  -- Show that it maps each index to the corresponding finite set
  intro i
  apply (u (Opposite.op ({ i } : Finset ι))).property.2
[GOAL]
case mp
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
⊢ ∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x
[PROOFSTEP]
haveI : ∀ ι' : (Finset ι)ᵒᵖ, Finite ((hallMatchingsFunctor t).obj ι') :=
  by
  intro ι'
  rw [hallMatchingsFunctor]
  infer_instance
    -- Apply the compactness argument
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
⊢ ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
[PROOFSTEP]
intro ι'
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
ι' : (Finset ι)ᵒᵖ
⊢ Finite ((hallMatchingsFunctor t).obj ι')
[PROOFSTEP]
rw [hallMatchingsFunctor]
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
ι' : (Finset ι)ᵒᵖ
⊢ Finite
    ((CategoryTheory.Functor.mk
          { obj := fun ι' => ↑(hallMatchingsOn t ι'.unop),
            map := fun {ι' ι''} g f => hallMatchingsOn.restrict t (_ : ι''.unop ≤ ι'.unop) f }).obj
      ι')
[PROOFSTEP]
infer_instance
  -- Apply the compactness argument
[GOAL]
case mp
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
⊢ ∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x
[PROOFSTEP]
obtain ⟨u, hu⟩ :=
  nonempty_sections_of_finite_inverse_system
    (hallMatchingsFunctor t)
      -- Interpret the resulting section of the inverse limit
[GOAL]
case mp.intro
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
⊢ ∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x
[PROOFSTEP]
refine' ⟨_, _, _⟩
[GOAL]
case mp.intro.refine'_1
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
⊢ ι → α
[PROOFSTEP]
exact fun i => (u (Opposite.op ({ i } : Finset ι))).val ⟨i, by simp only [Opposite.unop_op, mem_singleton]⟩
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i : ι
⊢ i ∈ (Opposite.op {i}).unop
[PROOFSTEP]
simp only [Opposite.unop_op, mem_singleton]
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
⊢ Function.Injective fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }
[PROOFSTEP]
intro i i'
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
⊢ (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i =
      (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i' →
    i = i'
[PROOFSTEP]
have subi : ({ i } : Finset ι) ⊆ { i, i' } := by simp
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
⊢ {i} ⊆ {i, i'}
[PROOFSTEP]
simp
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
subi : {i} ⊆ {i, i'}
⊢ (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i =
      (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i' →
    i = i'
[PROOFSTEP]
have subi' : ({ i' } : Finset ι) ⊆ { i, i' } := by simp
[GOAL]
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
subi : {i} ⊆ {i, i'}
⊢ {i'} ⊆ {i, i'}
[PROOFSTEP]
simp
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
subi : {i} ⊆ {i, i'}
subi' : {i'} ⊆ {i, i'}
⊢ (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i =
      (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i' →
    i = i'
[PROOFSTEP]
rw [← Finset.le_iff_subset] at subi subi'
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
subi : {i} ≤ {i, i'}
subi' : {i'} ≤ {i, i'}
⊢ (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i =
      (fun i => ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) }) i' →
    i = i'
[PROOFSTEP]
simp only
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
subi : {i} ≤ {i, i'}
subi' : {i'} ≤ {i, i'}
⊢ ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) } =
      ↑(u (Opposite.op {i'})) { val := i', property := (_ : i' ∈ {i'}) } →
    i = i'
[PROOFSTEP]
rw [← hu (CategoryTheory.homOfLE subi).op, ← hu (CategoryTheory.homOfLE subi').op]
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
subi : {i} ≤ {i, i'}
subi' : {i'} ≤ {i, i'}
⊢ ↑((hallMatchingsFunctor t).map (homOfLE subi).op (u (Opposite.op {i, i'}))) { val := i, property := (_ : i ∈ {i}) } =
      ↑((hallMatchingsFunctor t).map (homOfLE subi').op (u (Opposite.op {i, i'})))
        { val := i', property := (_ : i' ∈ {i'}) } →
    i = i'
[PROOFSTEP]
let uii' := u (Opposite.op ({ i, i' } : Finset ι))
[GOAL]
case mp.intro.refine'_2
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i i' : ι
subi : {i} ≤ {i, i'}
subi' : {i'} ≤ {i, i'}
uii' : (hallMatchingsFunctor t).obj (Opposite.op {i, i'}) := u (Opposite.op {i, i'})
⊢ ↑((hallMatchingsFunctor t).map (homOfLE subi).op (u (Opposite.op {i, i'}))) { val := i, property := (_ : i ∈ {i}) } =
      ↑((hallMatchingsFunctor t).map (homOfLE subi').op (u (Opposite.op {i, i'})))
        { val := i', property := (_ : i' ∈ {i'}) } →
    i = i'
[PROOFSTEP]
exact fun h => Subtype.mk_eq_mk.mp (uii'.property.1 h)
[GOAL]
case mp.intro.refine'_3
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
⊢ ∀ (x : ι), ↑(u (Opposite.op {x})) { val := x, property := (_ : x ∈ {x}) } ∈ t x
[PROOFSTEP]
intro i
[GOAL]
case mp.intro.refine'_3
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
h : ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
this✝ : ∀ (ι' : (Finset ι)ᵒᵖ), Nonempty ((hallMatchingsFunctor t).obj ι')
this : ∀ (ι' : (Finset ι)ᵒᵖ), Finite ((hallMatchingsFunctor t).obj ι')
u : (j : (Finset ι)ᵒᵖ) → (hallMatchingsFunctor t).obj j
hu : u ∈ Functor.sections (hallMatchingsFunctor t)
i : ι
⊢ ↑(u (Opposite.op {i})) { val := i, property := (_ : i ∈ {i}) } ∈ t i
[PROOFSTEP]
apply (u (Opposite.op ({ i } : Finset ι))).property.2
[GOAL]
case mpr
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
⊢ (∃ f, Function.Injective f ∧ ∀ (x : ι), f x ∈ t x) → ∀ (s : Finset ι), card s ≤ card (Finset.biUnion s t)
[PROOFSTEP]
rintro ⟨f, hf₁, hf₂⟩ s
[GOAL]
case mpr.intro.intro
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
f : ι → α
hf₁ : Function.Injective f
hf₂ : ∀ (x : ι), f x ∈ t x
s : Finset ι
⊢ card s ≤ card (Finset.biUnion s t)
[PROOFSTEP]
rw [← Finset.card_image_of_injective s hf₁]
[GOAL]
case mpr.intro.intro
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
f : ι → α
hf₁ : Function.Injective f
hf₂ : ∀ (x : ι), f x ∈ t x
s : Finset ι
⊢ card (image f s) ≤ card (Finset.biUnion s t)
[PROOFSTEP]
apply Finset.card_le_of_subset
[GOAL]
case mpr.intro.intro.a
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
f : ι → α
hf₁ : Function.Injective f
hf₂ : ∀ (x : ι), f x ∈ t x
s : Finset ι
⊢ image f s ⊆ Finset.biUnion s t
[PROOFSTEP]
intro
[GOAL]
case mpr.intro.intro.a
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
f : ι → α
hf₁ : Function.Injective f
hf₂ : ∀ (x : ι), f x ∈ t x
s : Finset ι
a✝ : α
⊢ a✝ ∈ image f s → a✝ ∈ Finset.biUnion s t
[PROOFSTEP]
rw [Finset.mem_image, Finset.mem_biUnion]
[GOAL]
case mpr.intro.intro.a
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
f : ι → α
hf₁ : Function.Injective f
hf₂ : ∀ (x : ι), f x ∈ t x
s : Finset ι
a✝ : α
⊢ (∃ a, a ∈ s ∧ f a = a✝) → ∃ a, a ∈ s ∧ a✝ ∈ t a
[PROOFSTEP]
rintro ⟨x, hx, rfl⟩
[GOAL]
case mpr.intro.intro.a.intro.intro
ι : Type u
α : Type v
inst✝ : DecidableEq α
t : ι → Finset α
f : ι → α
hf₁ : Function.Injective f
hf₂ : ∀ (x : ι), f x ∈ t x
s : Finset ι
x : ι
hx : x ∈ s
⊢ ∃ a, a ∈ s ∧ f x ∈ t a
[PROOFSTEP]
exact ⟨x, hx, hf₂ x⟩
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
A : Finset α
⊢ Fintype ↑(Rel.image r ↑A)
[PROOFSTEP]
have h : Rel.image r A = (A.biUnion fun a => (Rel.image r { a }).toFinset : Set β) :=
  by
  ext
    -- Porting note: added `Set.mem_toFinset`
  simp [Rel.image, (Set.mem_toFinset)]
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
A : Finset α
⊢ Rel.image r ↑A = ↑(Finset.biUnion A fun a => Set.toFinset (Rel.image r {a}))
[PROOFSTEP]
ext
  -- Porting note: added `Set.mem_toFinset`
[GOAL]
case h
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
A : Finset α
x✝ : β
⊢ x✝ ∈ Rel.image r ↑A ↔ x✝ ∈ ↑(Finset.biUnion A fun a => Set.toFinset (Rel.image r {a}))
[PROOFSTEP]
simp [Rel.image, (Set.mem_toFinset)]
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
A : Finset α
h : Rel.image r ↑A = ↑(Finset.biUnion A fun a => Set.toFinset (Rel.image r {a}))
⊢ Fintype ↑(Rel.image r ↑A)
[PROOFSTEP]
rw [h]
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
A : Finset α
h : Rel.image r ↑A = ↑(Finset.biUnion A fun a => Set.toFinset (Rel.image r {a}))
⊢ Fintype ↑↑(Finset.biUnion A fun a => Set.toFinset (Rel.image r {a}))
[PROOFSTEP]
apply FinsetCoe.fintype
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
⊢ (∀ (A : Finset α), Finset.card A ≤ card ↑(Rel.image r ↑A)) ↔ ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
let r' a := (Rel.image r { a }).toFinset
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
⊢ (∀ (A : Finset α), Finset.card A ≤ card ↑(Rel.image r ↑A)) ↔ ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
have h : ∀ A : Finset α, Fintype.card (Rel.image r A) = (A.biUnion r').card :=
  by
  intro A
  rw [← Set.toFinset_card]
  apply congr_arg
  ext b
  simp [Rel.image, (Set.mem_toFinset)]
    -- Porting note: added `Set.mem_toFinset`
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
⊢ ∀ (A : Finset α), card ↑(Rel.image r ↑A) = Finset.card (Finset.biUnion A r')
[PROOFSTEP]
intro A
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
A : Finset α
⊢ card ↑(Rel.image r ↑A) = Finset.card (Finset.biUnion A r')
[PROOFSTEP]
rw [← Set.toFinset_card]
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
A : Finset α
⊢ Finset.card (Set.toFinset (Rel.image r ↑A)) = Finset.card (Finset.biUnion A r')
[PROOFSTEP]
apply congr_arg
[GOAL]
case h
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
A : Finset α
⊢ Set.toFinset (Rel.image r ↑A) = Finset.biUnion A r'
[PROOFSTEP]
ext b
[GOAL]
case h.a
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
A : Finset α
b : β
⊢ b ∈ Set.toFinset (Rel.image r ↑A) ↔ b ∈ Finset.biUnion A r'
[PROOFSTEP]
simp [Rel.image, (Set.mem_toFinset)]
  -- Porting note: added `Set.mem_toFinset`
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
h : ∀ (A : Finset α), card ↑(Rel.image r ↑A) = Finset.card (Finset.biUnion A r')
⊢ (∀ (A : Finset α), Finset.card A ≤ card ↑(Rel.image r ↑A)) ↔ ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
have h' : ∀ (f : α → β) (x), r x (f x) ↔ f x ∈ r' x := by simp [Rel.image, (Set.mem_toFinset)]
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
h : ∀ (A : Finset α), card ↑(Rel.image r ↑A) = Finset.card (Finset.biUnion A r')
⊢ ∀ (f : α → β) (x : α), r x (f x) ↔ f x ∈ r' x
[PROOFSTEP]
simp [Rel.image, (Set.mem_toFinset)]
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
h : ∀ (A : Finset α), card ↑(Rel.image r ↑A) = Finset.card (Finset.biUnion A r')
h' : ∀ (f : α → β) (x : α), r x (f x) ↔ f x ∈ r' x
⊢ (∀ (A : Finset α), Finset.card A ≤ card ↑(Rel.image r ↑A)) ↔ ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
simp only [h, h']
[GOAL]
α : Type u
β : Type v
inst✝¹ : DecidableEq β
r : α → β → Prop
inst✝ : (a : α) → Fintype ↑(Rel.image r {a})
r' : α → Finset β := fun a => Set.toFinset (Rel.image r {a})
h : ∀ (A : Finset α), card ↑(Rel.image r ↑A) = Finset.card (Finset.biUnion A r')
h' : ∀ (f : α → β) (x : α), r x (f x) ↔ f x ∈ r' x
⊢ (∀ (A : Finset α), Finset.card A ≤ Finset.card (Finset.biUnion A fun a => Set.toFinset (Rel.image r {a}))) ↔
    ∃ f, Function.Injective f ∧ ∀ (x : α), f x ∈ Set.toFinset (Rel.image r {x})
[PROOFSTEP]
apply Finset.all_card_le_biUnion_card_iff_exists_injective
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
⊢ (∀ (A : Finset α), Finset.card A ≤ Finset.card (filter (fun b => ∃ a, a ∈ A ∧ r a b) univ)) ↔
    ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
haveI := Classical.decEq β
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
⊢ (∀ (A : Finset α), Finset.card A ≤ Finset.card (filter (fun b => ∃ a, a ∈ A ∧ r a b) univ)) ↔
    ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
let r' a := univ.filter fun b => r a b
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
⊢ (∀ (A : Finset α), Finset.card A ≤ Finset.card (filter (fun b => ∃ a, a ∈ A ∧ r a b) univ)) ↔
    ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
have h : ∀ A : Finset α, (univ.filter fun b : β => ∃ a ∈ A, r a b) = A.biUnion r' :=
  by
  intro A
  ext b
  simp
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
⊢ ∀ (A : Finset α), filter (fun b => ∃ a, a ∈ A ∧ r a b) univ = Finset.biUnion A r'
[PROOFSTEP]
intro A
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
A : Finset α
⊢ filter (fun b => ∃ a, a ∈ A ∧ r a b) univ = Finset.biUnion A r'
[PROOFSTEP]
ext b
[GOAL]
case a
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
A : Finset α
b : β
⊢ b ∈ filter (fun b => ∃ a, a ∈ A ∧ r a b) univ ↔ b ∈ Finset.biUnion A r'
[PROOFSTEP]
simp
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
h : ∀ (A : Finset α), filter (fun b => ∃ a, a ∈ A ∧ r a b) univ = Finset.biUnion A r'
⊢ (∀ (A : Finset α), Finset.card A ≤ Finset.card (filter (fun b => ∃ a, a ∈ A ∧ r a b) univ)) ↔
    ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
have h' : ∀ (f : α → β) (x), r x (f x) ↔ f x ∈ r' x := by simp
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
h : ∀ (A : Finset α), filter (fun b => ∃ a, a ∈ A ∧ r a b) univ = Finset.biUnion A r'
⊢ ∀ (f : α → β) (x : α), r x (f x) ↔ f x ∈ r' x
[PROOFSTEP]
simp
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
h : ∀ (A : Finset α), filter (fun b => ∃ a, a ∈ A ∧ r a b) univ = Finset.biUnion A r'
h' : ∀ (f : α → β) (x : α), r x (f x) ↔ f x ∈ r' x
⊢ (∀ (A : Finset α), Finset.card A ≤ Finset.card (filter (fun b => ∃ a, a ∈ A ∧ r a b) univ)) ↔
    ∃ f, Function.Injective f ∧ ∀ (x : α), r x (f x)
[PROOFSTEP]
simp_rw [h, h']
[GOAL]
α : Type u
β : Type v
inst✝¹ : Fintype β
r : α → β → Prop
inst✝ : (a : α) → DecidablePred (r a)
this : DecidableEq β
r' : α → Finset β := fun a => filter (fun b => r a b) univ
h : ∀ (A : Finset α), filter (fun b => ∃ a, a ∈ A ∧ r a b) univ = Finset.biUnion A r'
h' : ∀ (f : α → β) (x : α), r x (f x) ↔ f x ∈ r' x
⊢ (∀ (A : Finset α), Finset.card A ≤ Finset.card (Finset.biUnion A fun a => filter (fun b => r a b) univ)) ↔
    ∃ f, Function.Injective f ∧ ∀ (x : α), f x ∈ filter (fun b => r x b) univ
[PROOFSTEP]
apply Finset.all_card_le_biUnion_card_iff_exists_injective


[GOAL]
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
⊢ ∃ b, ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
[PROOFSTEP]
by_cases h : ∃ b, (a, b) ∈ f.val
[GOAL]
case pos
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ∃ b, (a, b) ∈ ↑f
⊢ ∃ b, ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
[PROOFSTEP]
cases' h with b hb
[GOAL]
case pos.intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
b : β
hb : (a, b) ∈ ↑f
⊢ ∃ b, ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
[PROOFSTEP]
exact ⟨b, fun p hp ↦ f.prop _ hp _ hb⟩
[GOAL]
case neg
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
⊢ ∃ b, ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
[PROOFSTEP]
have :
  ∀ x ∈ (f.val.filter fun p : α × β ↦ p.fst < a).image Prod.snd,
    ∀ y ∈ (f.val.filter fun p : α × β ↦ a < p.fst).image Prod.snd, x < y :=
  by
  intro x hx y hy
  rw [Finset.mem_image] at hx hy
  rcases hx with ⟨p, hp1, rfl⟩
  rcases hy with ⟨q, hq1, rfl⟩
  rw [Finset.mem_filter] at hp1 hq1
  rw [← lt_iff_lt_of_cmp_eq_cmp (f.prop _ hp1.1 _ hq1.1)]
  exact lt_trans hp1.right hq1.right
[GOAL]
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
⊢ ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
[PROOFSTEP]
intro x hx y hy
[GOAL]
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
x : β
hx : x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f)
y : β
hy : y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f)
⊢ x < y
[PROOFSTEP]
rw [Finset.mem_image] at hx hy
[GOAL]
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
x : β
hx : ∃ a_1, a_1 ∈ Finset.filter (fun p => p.fst < a) ↑f ∧ a_1.snd = x
y : β
hy : ∃ a_1, a_1 ∈ Finset.filter (fun p => a < p.fst) ↑f ∧ a_1.snd = y
⊢ x < y
[PROOFSTEP]
rcases hx with ⟨p, hp1, rfl⟩
[GOAL]
case intro.intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
y : β
hy : ∃ a_1, a_1 ∈ Finset.filter (fun p => a < p.fst) ↑f ∧ a_1.snd = y
p : α × β
hp1 : p ∈ Finset.filter (fun p => p.fst < a) ↑f
⊢ p.snd < y
[PROOFSTEP]
rcases hy with ⟨q, hq1, rfl⟩
[GOAL]
case intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
p : α × β
hp1 : p ∈ Finset.filter (fun p => p.fst < a) ↑f
q : α × β
hq1 : q ∈ Finset.filter (fun p => a < p.fst) ↑f
⊢ p.snd < q.snd
[PROOFSTEP]
rw [Finset.mem_filter] at hp1 hq1
[GOAL]
case intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
p : α × β
hp1 : p ∈ ↑f ∧ p.fst < a
q : α × β
hq1 : q ∈ ↑f ∧ a < q.fst
⊢ p.snd < q.snd
[PROOFSTEP]
rw [← lt_iff_lt_of_cmp_eq_cmp (f.prop _ hp1.1 _ hq1.1)]
[GOAL]
case intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
p : α × β
hp1 : p ∈ ↑f ∧ p.fst < a
q : α × β
hq1 : q ∈ ↑f ∧ a < q.fst
⊢ p.fst < q.fst
[PROOFSTEP]
exact lt_trans hp1.right hq1.right
[GOAL]
case neg
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
⊢ ∃ b, ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
[PROOFSTEP]
cases' exists_between_finsets _ _ this with b hb
[GOAL]
case neg.intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
⊢ ∃ b, ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
[PROOFSTEP]
use b
[GOAL]
case h
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
⊢ ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
[PROOFSTEP]
rintro ⟨p1, p2⟩ hp
[GOAL]
case h.mk
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
have : p1 ≠ a := fun he ↦ h ⟨p2, he ▸ hp⟩
[GOAL]
case h.mk
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this✝ :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
this : p1 ≠ a
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
cases' lt_or_gt_of_ne this with hl hr
[GOAL]
case h.mk.inl
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this✝ :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
this : p1 ≠ a
hl : p1 < a
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
have : p1 < a ∧ p2 < b := ⟨hl, hb.1 _ (Finset.mem_image.mpr ⟨(p1, p2), Finset.mem_filter.mpr ⟨hp, hl⟩, rfl⟩)⟩
[GOAL]
case h.mk.inl
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this✝¹ :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
this✝ : p1 ≠ a
hl : p1 < a
this : p1 < a ∧ p2 < b
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
rw [← cmp_eq_lt_iff, ← cmp_eq_lt_iff] at this
[GOAL]
case h.mk.inl
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this✝¹ :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
this✝ : p1 ≠ a
hl : p1 < a
this : cmp p1 a = Ordering.lt ∧ cmp p2 b = Ordering.lt
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
exact this.1.trans this.2.symm
[GOAL]
case h.mk.inr
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this✝ :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
this : p1 ≠ a
hr : p1 > a
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
have : a < p1 ∧ b < p2 := ⟨hr, hb.2 _ (Finset.mem_image.mpr ⟨(p1, p2), Finset.mem_filter.mpr ⟨hp, hr⟩, rfl⟩)⟩
[GOAL]
case h.mk.inr
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this✝¹ :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
this✝ : p1 ≠ a
hr : p1 > a
this : a < p1 ∧ b < p2
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
rw [← cmp_eq_gt_iff, ← cmp_eq_gt_iff] at this
[GOAL]
case h.mk.inr
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
f : PartialIso α β
a : α
h : ¬∃ b, (a, b) ∈ ↑f
this✝¹ :
  ∀ (x : β),
    x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) →
      ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → x < y
b : β
hb :
  (∀ (x : β), x ∈ Finset.image Prod.snd (Finset.filter (fun p => p.fst < a) ↑f) → x < b) ∧
    ∀ (y : β), y ∈ Finset.image Prod.snd (Finset.filter (fun p => a < p.fst) ↑f) → b < y
p1 : α
p2 : β
hp : (p1, p2) ∈ ↑f
this✝ : p1 ≠ a
hr : p1 > a
this : cmp p1 a = Ordering.gt ∧ cmp p2 b = Ordering.gt
⊢ cmp (p1, p2).fst a = cmp (p1, p2).snd b
[PROOFSTEP]
exact this.1.trans this.2.symm
[GOAL]
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : Finset (α × β)
hf : ∀ (p : α × β), p ∈ f → ∀ (q : α × β), q ∈ f → cmp p.fst q.fst = cmp p.snd q.snd
p : β × α
hp : p ∈ Finset.image (↑(Equiv.prodComm α β)) f
q : β × α
hq : q ∈ Finset.image (↑(Equiv.prodComm α β)) f
⊢ ↑(Equiv.prodComm α β).symm p ∈ f
[PROOFSTEP]
rw [← Finset.mem_coe, Finset.coe_image, Equiv.image_eq_preimage] at hp
[GOAL]
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : Finset (α × β)
hf : ∀ (p : α × β), p ∈ f → ∀ (q : α × β), q ∈ f → cmp p.fst q.fst = cmp p.snd q.snd
p : β × α
hp : p ∈ ↑(Equiv.prodComm α β).symm ⁻¹' ↑f
q : β × α
hq : q ∈ Finset.image (↑(Equiv.prodComm α β)) f
⊢ ↑(Equiv.prodComm α β).symm p ∈ f
[PROOFSTEP]
rwa [← Finset.mem_coe]
[GOAL]
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : Finset (α × β)
hf : ∀ (p : α × β), p ∈ f → ∀ (q : α × β), q ∈ f → cmp p.fst q.fst = cmp p.snd q.snd
p : β × α
hp : p ∈ Finset.image (↑(Equiv.prodComm α β)) f
q : β × α
hq : q ∈ Finset.image (↑(Equiv.prodComm α β)) f
⊢ ↑(Equiv.prodComm α β).symm q ∈ f
[PROOFSTEP]
rw [← Finset.mem_coe, Finset.coe_image, Equiv.image_eq_preimage] at hq
[GOAL]
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : Finset (α × β)
hf : ∀ (p : α × β), p ∈ f → ∀ (q : α × β), q ∈ f → cmp p.fst q.fst = cmp p.snd q.snd
p : β × α
hp : p ∈ Finset.image (↑(Equiv.prodComm α β)) f
q : β × α
hq : q ∈ ↑(Equiv.prodComm α β).symm ⁻¹' ↑f
⊢ ↑(Equiv.prodComm α β).symm q ∈ f
[PROOFSTEP]
rwa [← Finset.mem_coe]
[GOAL]
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
⊢ ∃ y, y ∈ {f | ∃ b, (a, b) ∈ ↑f} ∧ f ≤ y
[PROOFSTEP]
cases' exists_across f a with b a_b
[GOAL]
case intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
⊢ ∃ y, y ∈ {f | ∃ b, (a, b) ∈ ↑f} ∧ f ≤ y
[PROOFSTEP]
refine ⟨⟨insert (a, b) f.val, fun p hp q hq ↦ ?_⟩, ⟨b, Finset.mem_insert_self _ _⟩, Finset.subset_insert _ _⟩
[GOAL]
case intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
p : α × β
hp : p ∈ insert (a, b) ↑f
q : α × β
hq : q ∈ insert (a, b) ↑f
⊢ cmp p.fst q.fst = cmp p.snd q.snd
[PROOFSTEP]
rw [Finset.mem_insert] at hp hq
[GOAL]
case intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
p : α × β
hp : p = (a, b) ∨ p ∈ ↑f
q : α × β
hq : q = (a, b) ∨ q ∈ ↑f
⊢ cmp p.fst q.fst = cmp p.snd q.snd
[PROOFSTEP]
rcases hp with (rfl | pf)
[GOAL]
case intro.inl
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
q : α × β
hq : q = (a, b) ∨ q ∈ ↑f
⊢ cmp (a, b).fst q.fst = cmp (a, b).snd q.snd
[PROOFSTEP]
rcases hq with (rfl | qf)
[GOAL]
case intro.inr
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
p q : α × β
hq : q = (a, b) ∨ q ∈ ↑f
pf : p ∈ ↑f
⊢ cmp p.fst q.fst = cmp p.snd q.snd
[PROOFSTEP]
rcases hq with (rfl | qf)
[GOAL]
case intro.inl.inl
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
⊢ cmp (a, b).fst (a, b).fst = cmp (a, b).snd (a, b).snd
[PROOFSTEP]
simp only [cmp_self_eq_eq]
[GOAL]
case intro.inl.inr
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
q : α × β
qf : q ∈ ↑f
⊢ cmp (a, b).fst q.fst = cmp (a, b).snd q.snd
[PROOFSTEP]
rw [cmp_eq_cmp_symm]
[GOAL]
case intro.inl.inr
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
q : α × β
qf : q ∈ ↑f
⊢ cmp q.fst (a, b).fst = cmp q.snd (a, b).snd
[PROOFSTEP]
exact a_b _ qf
[GOAL]
case intro.inr.inl
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
p : α × β
pf : p ∈ ↑f
⊢ cmp p.fst (a, b).fst = cmp p.snd (a, b).snd
[PROOFSTEP]
exact a_b _ pf
[GOAL]
case intro.inr.inr
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
a : α
f : PartialIso α β
b : β
a_b : ∀ (p : α × β), p ∈ ↑f → cmp p.fst a = cmp p.snd b
p q : α × β
pf : p ∈ ↑f
qf : q ∈ ↑f
⊢ cmp p.fst q.fst = cmp p.snd q.snd
[PROOFSTEP]
exact f.prop _ pf _ qf
[GOAL]
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered α
inst✝² : NoMinOrder α
inst✝¹ : NoMaxOrder α
inst✝ : Nonempty α
b : β
f : PartialIso α β
⊢ ∃ y, y ∈ {f | ∃ a, (a, b) ∈ ↑f} ∧ f ≤ y
[PROOFSTEP]
rcases(definedAtLeft α b).mem_gt f.comm with ⟨f', ⟨a, ha⟩, hl⟩
[GOAL]
case intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered α
inst✝² : NoMinOrder α
inst✝¹ : NoMaxOrder α
inst✝ : Nonempty α
b : β
f : PartialIso α β
f' : PartialIso β α
hl : PartialIso.comm f ≤ f'
a : α
ha : (b, a) ∈ ↑f'
⊢ ∃ y, y ∈ {f | ∃ a, (a, b) ∈ ↑f} ∧ f ≤ y
[PROOFSTEP]
refine' ⟨f'.comm, ⟨a, _⟩, _⟩
[GOAL]
case intro.intro.intro.refine'_1
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered α
inst✝² : NoMinOrder α
inst✝¹ : NoMaxOrder α
inst✝ : Nonempty α
b : β
f : PartialIso α β
f' : PartialIso β α
hl : PartialIso.comm f ≤ f'
a : α
ha : (b, a) ∈ ↑f'
⊢ (a, b) ∈ ↑(PartialIso.comm f')
[PROOFSTEP]
change (a, b) ∈ f'.val.image _
[GOAL]
case intro.intro.intro.refine'_1
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered α
inst✝² : NoMinOrder α
inst✝¹ : NoMaxOrder α
inst✝ : Nonempty α
b : β
f : PartialIso α β
f' : PartialIso β α
hl : PartialIso.comm f ≤ f'
a : α
ha : (b, a) ∈ ↑f'
⊢ (a, b) ∈ Finset.image ↑(Equiv.prodComm β α) ↑f'
[PROOFSTEP]
rwa [← Finset.mem_coe, Finset.coe_image, Equiv.image_eq_preimage]
[GOAL]
case intro.intro.intro.refine'_2
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered α
inst✝² : NoMinOrder α
inst✝¹ : NoMaxOrder α
inst✝ : Nonempty α
b : β
f : PartialIso α β
f' : PartialIso β α
hl : PartialIso.comm f ≤ f'
a : α
ha : (b, a) ∈ ↑f'
⊢ f ≤ PartialIso.comm f'
[PROOFSTEP]
change _ ⊆ f'.val.image _
[GOAL]
case intro.intro.intro.refine'_2
α : Type u_1
β : Type u_2
inst✝⁵ : LinearOrder α
inst✝⁴ : LinearOrder β
inst✝³ : DenselyOrdered α
inst✝² : NoMinOrder α
inst✝¹ : NoMaxOrder α
inst✝ : Nonempty α
b : β
f : PartialIso α β
f' : PartialIso β α
hl : PartialIso.comm f ≤ f'
a : α
ha : (b, a) ∈ ↑f'
⊢ (fun a => ↑a) f ⊆ Finset.image ↑(Equiv.prodComm β α) ↑f'
[PROOFSTEP]
rwa [← Finset.coe_subset, Finset.coe_image, ← Equiv.subset_image, ← Finset.coe_image, Finset.coe_subset]
[GOAL]
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
⊢ Nonempty (α ↪o β)
[PROOFSTEP]
rcases exists_pair_lt β with ⟨x, y, hxy⟩
[GOAL]
case intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
⊢ Nonempty (α ↪o β)
[PROOFSTEP]
cases' exists_between hxy with a ha
[GOAL]
case intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
⊢ Nonempty (α ↪o β)
[PROOFSTEP]
haveI : Nonempty (Set.Ioo x y) := ⟨⟨a, ha⟩⟩
[GOAL]
case intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
this : Nonempty ↑(Set.Ioo x y)
⊢ Nonempty (α ↪o β)
[PROOFSTEP]
let our_ideal : Ideal (PartialIso α _) := idealOfCofinals default (definedAtLeft (Set.Ioo x y))
[GOAL]
case intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
this : Nonempty ↑(Set.Ioo x y)
our_ideal : Ideal (PartialIso α ↑(Set.Ioo x y)) := idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y))
⊢ Nonempty (α ↪o β)
[PROOFSTEP]
let F a := funOfIdeal a our_ideal (cofinal_meets_idealOfCofinals _ _ a)
[GOAL]
case intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
this : Nonempty ↑(Set.Ioo x y)
our_ideal : Ideal (PartialIso α ↑(Set.Ioo x y)) := idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y))
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a =>
    funOfIdeal a our_ideal
      (_ : ∃ x_1, x_1 ∈ definedAtLeft (↑(Set.Ioo x y)) a ∧ x_1 ∈ idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y)))
⊢ Nonempty (α ↪o β)
[PROOFSTEP]
refine ⟨RelEmbedding.trans (OrderEmbedding.ofStrictMono (fun a ↦ (F a).val) fun a₁ a₂ ↦ ?_) (OrderEmbedding.subtype _)⟩
[GOAL]
case intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
this : Nonempty ↑(Set.Ioo x y)
our_ideal : Ideal (PartialIso α ↑(Set.Ioo x y)) := idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y))
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a =>
    funOfIdeal a our_ideal
      (_ : ∃ x_1, x_1 ∈ definedAtLeft (↑(Set.Ioo x y)) a ∧ x_1 ∈ idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y)))
a₁ a₂ : α
⊢ a₁ < a₂ → (fun a => ↑(F a)) a₁ < (fun a => ↑(F a)) a₂
[PROOFSTEP]
rcases(F a₁).prop with ⟨f, hf, ha₁⟩
[GOAL]
case intro.intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
this : Nonempty ↑(Set.Ioo x y)
our_ideal : Ideal (PartialIso α ↑(Set.Ioo x y)) := idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y))
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a =>
    funOfIdeal a our_ideal
      (_ : ∃ x_1, x_1 ∈ definedAtLeft (↑(Set.Ioo x y)) a ∧ x_1 ∈ idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y)))
a₁ a₂ : α
f : PartialIso α ↑(Set.Ioo x y)
hf : f ∈ our_ideal
ha₁ : (a₁, ↑(F a₁)) ∈ ↑f
⊢ a₁ < a₂ → (fun a => ↑(F a)) a₁ < (fun a => ↑(F a)) a₂
[PROOFSTEP]
rcases(F a₂).prop with ⟨g, hg, ha₂⟩
[GOAL]
case intro.intro.intro.intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
this : Nonempty ↑(Set.Ioo x y)
our_ideal : Ideal (PartialIso α ↑(Set.Ioo x y)) := idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y))
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a =>
    funOfIdeal a our_ideal
      (_ : ∃ x_1, x_1 ∈ definedAtLeft (↑(Set.Ioo x y)) a ∧ x_1 ∈ idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y)))
a₁ a₂ : α
f : PartialIso α ↑(Set.Ioo x y)
hf : f ∈ our_ideal
ha₁ : (a₁, ↑(F a₁)) ∈ ↑f
g : PartialIso α ↑(Set.Ioo x y)
hg : g ∈ our_ideal
ha₂ : (a₂, ↑(F a₂)) ∈ ↑g
⊢ a₁ < a₂ → (fun a => ↑(F a)) a₁ < (fun a => ↑(F a)) a₂
[PROOFSTEP]
rcases our_ideal.directed _ hf _ hg with ⟨m, _hm, fm, gm⟩
[GOAL]
case intro.intro.intro.intro.intro.intro.intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝⁴ : LinearOrder α
inst✝³ : LinearOrder β
inst✝² : Encodable α
inst✝¹ : DenselyOrdered β
inst✝ : Nontrivial β
x y : β
hxy : x < y
a : β
ha : x < a ∧ a < y
this : Nonempty ↑(Set.Ioo x y)
our_ideal : Ideal (PartialIso α ↑(Set.Ioo x y)) := idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y))
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a =>
    funOfIdeal a our_ideal
      (_ : ∃ x_1, x_1 ∈ definedAtLeft (↑(Set.Ioo x y)) a ∧ x_1 ∈ idealOfCofinals default (definedAtLeft ↑(Set.Ioo x y)))
a₁ a₂ : α
f : PartialIso α ↑(Set.Ioo x y)
hf : f ∈ our_ideal
ha₁ : (a₁, ↑(F a₁)) ∈ ↑f
g : PartialIso α ↑(Set.Ioo x y)
hg : g ∈ our_ideal
ha₂ : (a₂, ↑(F a₂)) ∈ ↑g
m : PartialIso α ↑(Set.Ioo x y)
_hm : m ∈ ↑our_ideal
fm : f ≤ m
gm : g ≤ m
⊢ a₁ < a₂ → (fun a => ↑(F a)) a₁ < (fun a => ↑(F a)) a₂
[PROOFSTEP]
exact (lt_iff_lt_of_cmp_eq_cmp <| m.prop (a₁, _) (fm ha₁) (a₂, _) (gm ha₂)).mp
[GOAL]
α : Type u_1
β : Type u_2
inst✝¹¹ : LinearOrder α
inst✝¹⁰ : LinearOrder β
inst✝⁹ : Encodable α
inst✝⁸ : DenselyOrdered α
inst✝⁷ : NoMinOrder α
inst✝⁶ : NoMaxOrder α
inst✝⁵ : Nonempty α
inst✝⁴ : Encodable β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
to_cofinal : α ⊕ β → Cofinal (PartialIso α β) := fun p => Sum.recOn p (definedAtLeft β) (definedAtRight α)
our_ideal : Ideal (PartialIso α β) := idealOfCofinals default to_cofinal
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a => funOfIdeal a our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inl a) ∧ x ∈ idealOfCofinals default to_cofinal)
G : (b : β) → { a // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun b => invOfIdeal b our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inr b) ∧ x ∈ idealOfCofinals default to_cofinal)
a : α
b : β
⊢ cmp a ((fun b => ↑(G b)) b) = cmp ((fun a => ↑(F a)) a) b
[PROOFSTEP]
rcases(F a).prop with ⟨f, hf, ha⟩
[GOAL]
case intro.intro
α : Type u_1
β : Type u_2
inst✝¹¹ : LinearOrder α
inst✝¹⁰ : LinearOrder β
inst✝⁹ : Encodable α
inst✝⁸ : DenselyOrdered α
inst✝⁷ : NoMinOrder α
inst✝⁶ : NoMaxOrder α
inst✝⁵ : Nonempty α
inst✝⁴ : Encodable β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
to_cofinal : α ⊕ β → Cofinal (PartialIso α β) := fun p => Sum.recOn p (definedAtLeft β) (definedAtRight α)
our_ideal : Ideal (PartialIso α β) := idealOfCofinals default to_cofinal
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a => funOfIdeal a our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inl a) ∧ x ∈ idealOfCofinals default to_cofinal)
G : (b : β) → { a // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun b => invOfIdeal b our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inr b) ∧ x ∈ idealOfCofinals default to_cofinal)
a : α
b : β
f : PartialIso α β
hf : f ∈ our_ideal
ha : (a, ↑(F a)) ∈ ↑f
⊢ cmp a ((fun b => ↑(G b)) b) = cmp ((fun a => ↑(F a)) a) b
[PROOFSTEP]
rcases(G b).prop with ⟨g, hg, hb⟩
[GOAL]
case intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝¹¹ : LinearOrder α
inst✝¹⁰ : LinearOrder β
inst✝⁹ : Encodable α
inst✝⁸ : DenselyOrdered α
inst✝⁷ : NoMinOrder α
inst✝⁶ : NoMaxOrder α
inst✝⁵ : Nonempty α
inst✝⁴ : Encodable β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
to_cofinal : α ⊕ β → Cofinal (PartialIso α β) := fun p => Sum.recOn p (definedAtLeft β) (definedAtRight α)
our_ideal : Ideal (PartialIso α β) := idealOfCofinals default to_cofinal
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a => funOfIdeal a our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inl a) ∧ x ∈ idealOfCofinals default to_cofinal)
G : (b : β) → { a // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun b => invOfIdeal b our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inr b) ∧ x ∈ idealOfCofinals default to_cofinal)
a : α
b : β
f : PartialIso α β
hf : f ∈ our_ideal
ha : (a, ↑(F a)) ∈ ↑f
g : PartialIso α β
hg : g ∈ our_ideal
hb : (↑(G b), b) ∈ ↑g
⊢ cmp a ((fun b => ↑(G b)) b) = cmp ((fun a => ↑(F a)) a) b
[PROOFSTEP]
rcases our_ideal.directed _ hf _ hg with ⟨m, _, fm, gm⟩
[GOAL]
case intro.intro.intro.intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝¹¹ : LinearOrder α
inst✝¹⁰ : LinearOrder β
inst✝⁹ : Encodable α
inst✝⁸ : DenselyOrdered α
inst✝⁷ : NoMinOrder α
inst✝⁶ : NoMaxOrder α
inst✝⁵ : Nonempty α
inst✝⁴ : Encodable β
inst✝³ : DenselyOrdered β
inst✝² : NoMinOrder β
inst✝¹ : NoMaxOrder β
inst✝ : Nonempty β
to_cofinal : α ⊕ β → Cofinal (PartialIso α β) := fun p => Sum.recOn p (definedAtLeft β) (definedAtRight α)
our_ideal : Ideal (PartialIso α β) := idealOfCofinals default to_cofinal
F : (a : α) → { b // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun a => funOfIdeal a our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inl a) ∧ x ∈ idealOfCofinals default to_cofinal)
G : (b : β) → { a // ∃ f, f ∈ our_ideal ∧ (a, b) ∈ ↑f } :=
  fun b => invOfIdeal b our_ideal (_ : ∃ x, x ∈ to_cofinal (Sum.inr b) ∧ x ∈ idealOfCofinals default to_cofinal)
a : α
b : β
f : PartialIso α β
hf : f ∈ our_ideal
ha : (a, ↑(F a)) ∈ ↑f
g : PartialIso α β
hg : g ∈ our_ideal
hb : (↑(G b), b) ∈ ↑g
m : PartialIso α β
left✝ : m ∈ ↑our_ideal
fm : f ≤ m
gm : g ≤ m
⊢ cmp a ((fun b => ↑(G b)) b) = cmp ((fun a => ↑(F a)) a) b
[PROOFSTEP]
exact m.prop (a, _) (fm ha) (_, b) (gm hb)


[GOAL]
p : Prop
as ps as₁ : List Prop
⊢ as = List.reverseAux as₁ ps → implies (mk as) p ps (List.length as₁) → p
[PROOFSTEP]
induction ps generalizing as₁ with
| nil => exact fun _ ↦ id
| cons a as ih =>
  refine fun e H ↦ @ih (a :: as₁) e (H ?_)
  subst e; clear ih H
  suffices ∀ n n', n' = List.length as₁ + n → ∀ bs, mk (as₁.reverseAux bs) n' ↔ mk bs n from this 0 _ rfl (a :: as)
  induction as₁ with simp
  | cons b as₁ ih => exact fun n bs ↦ ih (n + 1) _ (Nat.succ_add ..) _
[GOAL]
p : Prop
as ps as₁ : List Prop
⊢ as = List.reverseAux as₁ ps → implies (mk as) p ps (List.length as₁) → p
[PROOFSTEP]
induction ps generalizing as₁ with
| nil => exact fun _ ↦ id
| cons a as ih =>
  refine fun e H ↦ @ih (a :: as₁) e (H ?_)
  subst e; clear ih H
  suffices ∀ n n', n' = List.length as₁ + n → ∀ bs, mk (as₁.reverseAux bs) n' ↔ mk bs n from this 0 _ rfl (a :: as)
  induction as₁ with simp
  | cons b as₁ ih => exact fun n bs ↦ ih (n + 1) _ (Nat.succ_add ..) _
[GOAL]
case nil
p : Prop
as as₁ : List Prop
⊢ as = List.reverseAux as₁ [] → implies (mk as) p [] (List.length as₁) → p
[PROOFSTEP]

| nil => exact fun _ ↦ id
[GOAL]
case nil
p : Prop
as as₁ : List Prop
⊢ as = List.reverseAux as₁ [] → implies (mk as) p [] (List.length as₁) → p
[PROOFSTEP]
exact fun _ ↦ id
[GOAL]
case cons
p : Prop
as✝ : List Prop
a : Prop
as : List Prop
ih : ∀ (as₁ : List Prop), as✝ = List.reverseAux as₁ as → implies (mk as✝) p as (List.length as₁) → p
as₁ : List Prop
⊢ as✝ = List.reverseAux as₁ (a :: as) → implies (mk as✝) p (a :: as) (List.length as₁) → p
[PROOFSTEP]

| cons a as ih =>
  refine fun e H ↦ @ih (a :: as₁) e (H ?_)
  subst e; clear ih H
  suffices ∀ n n', n' = List.length as₁ + n → ∀ bs, mk (as₁.reverseAux bs) n' ↔ mk bs n from this 0 _ rfl (a :: as)
  induction as₁ with simp
  | cons b as₁ ih => exact fun n bs ↦ ih (n + 1) _ (Nat.succ_add ..) _
[GOAL]
case cons
p : Prop
as✝ : List Prop
a : Prop
as : List Prop
ih : ∀ (as₁ : List Prop), as✝ = List.reverseAux as₁ as → implies (mk as✝) p as (List.length as₁) → p
as₁ : List Prop
⊢ as✝ = List.reverseAux as₁ (a :: as) → implies (mk as✝) p (a :: as) (List.length as₁) → p
[PROOFSTEP]
refine fun e H ↦ @ih (a :: as₁) e (H ?_)
[GOAL]
case cons
p : Prop
as✝ : List Prop
a : Prop
as : List Prop
ih : ∀ (as₁ : List Prop), as✝ = List.reverseAux as₁ as → implies (mk as✝) p as (List.length as₁) → p
as₁ : List Prop
e : as✝ = List.reverseAux as₁ (a :: as)
H : implies (mk as✝) p (a :: as) (List.length as₁)
⊢ mk as✝ (List.length as₁) ↔ a
[PROOFSTEP]
subst e
[GOAL]
case cons
p a : Prop
as as₁ : List Prop
ih :
  ∀ (as₁_1 : List Prop),
    List.reverseAux as₁ (a :: as) = List.reverseAux as₁_1 as →
      implies (mk (List.reverseAux as₁ (a :: as))) p as (List.length as₁_1) → p
H : implies (mk (List.reverseAux as₁ (a :: as))) p (a :: as) (List.length as₁)
⊢ mk (List.reverseAux as₁ (a :: as)) (List.length as₁) ↔ a
[PROOFSTEP]
clear ih H
[GOAL]
case cons
p a : Prop
as as₁ : List Prop
⊢ mk (List.reverseAux as₁ (a :: as)) (List.length as₁) ↔ a
[PROOFSTEP]
suffices ∀ n n', n' = List.length as₁ + n → ∀ bs, mk (as₁.reverseAux bs) n' ↔ mk bs n from this 0 _ rfl (a :: as)
[GOAL]
case cons
p a : Prop
as as₁ : List Prop
⊢ ∀ (n n' : ℕ), n' = List.length as₁ + n → ∀ (bs : List Prop), mk (List.reverseAux as₁ bs) n' ↔ mk bs n
[PROOFSTEP]
induction as₁ with simp
| cons b as₁ ih => exact fun n bs ↦ ih (n + 1) _ (Nat.succ_add ..) _
[GOAL]
case cons
p a : Prop
as as₁ : List Prop
⊢ ∀ (n n' : ℕ), n' = List.length as₁ + n → ∀ (bs : List Prop), mk (List.reverseAux as₁ bs) n' ↔ mk bs n
[PROOFSTEP]
induction as₁ with simp
| cons b as₁ ih => exact fun n bs ↦ ih (n + 1) _ (Nat.succ_add ..) _
[GOAL]
case cons.cons
p a : Prop
as : List Prop
b : Prop
as₁ : List Prop
ih : ∀ (n n' : ℕ), n' = List.length as₁ + n → ∀ (bs : List Prop), mk (List.reverseAux as₁ bs) n' ↔ mk bs n
⊢ ∀ (n n' : ℕ), n' = List.length (b :: as₁) + n → ∀ (bs : List Prop), mk (List.reverseAux (b :: as₁) bs) n' ↔ mk bs n
[PROOFSTEP]
simp
[GOAL]
case cons.cons
p a : Prop
as : List Prop
b : Prop
as₁ : List Prop
ih : ∀ (n n' : ℕ), n' = List.length as₁ + n → ∀ (bs : List Prop), mk (List.reverseAux as₁ bs) n' ↔ mk bs n
⊢ ∀ (n : ℕ) (bs : List Prop), mk (List.reverseAux as₁ (b :: bs)) (Nat.succ (List.length as₁) + n) ↔ mk bs n
[PROOFSTEP]

| cons b as₁ ih => exact fun n bs ↦ ih (n + 1) _ (Nat.succ_add ..) _
[GOAL]
case cons.cons
p a : Prop
as : List Prop
b : Prop
as₁ : List Prop
ih : ∀ (n n' : ℕ), n' = List.length as₁ + n → ∀ (bs : List Prop), mk (List.reverseAux as₁ bs) n' ↔ mk bs n
⊢ ∀ (n : ℕ) (bs : List Prop), mk (List.reverseAux as₁ (b :: bs)) (Nat.succ (List.length as₁) + n) ↔ mk bs n
[PROOFSTEP]
exact fun n bs ↦ ih (n + 1) _ (Nat.succ_add ..) _
[GOAL]
case cons.nil
p a : Prop
as : List Prop
⊢ ∀ (n n' : ℕ), n' = List.length [] + n → ∀ (bs : List Prop), mk (List.reverseAux [] bs) n' ↔ mk bs n
[PROOFSTEP]
simp
[GOAL]
v : Valuation
f₁ : Fmla
a : Prop
f₂ : Fmla
b : Prop
h₁ : reify v f₁ a
h₂ : reify v f₂ b
⊢ reify v (and f₁ f₂) (a ∨ b)
[PROOFSTEP]
refine ⟨fun H ↦ by_contra fun hn ↦ H ⟨fun c h ↦ by_contra fun hn' ↦ ?_⟩⟩
[GOAL]
v : Valuation
f₁ : Fmla
a : Prop
f₂ : Fmla
b : Prop
h₁ : reify v f₁ a
h₂ : reify v f₂ b
H : ¬Valuation.satisfies_fmla v (and f₁ f₂)
hn : ¬(a ∨ b)
c : Clause
h : c ∈ and f₁ f₂
hn' : ¬Valuation.satisfies v c
⊢ False
[PROOFSTEP]
rcases List.mem_append.1 h with h | h
[GOAL]
case inl
v : Valuation
f₁ : Fmla
a : Prop
f₂ : Fmla
b : Prop
h₁ : reify v f₁ a
h₂ : reify v f₂ b
H : ¬Valuation.satisfies_fmla v (and f₁ f₂)
hn : ¬(a ∨ b)
c : Clause
h✝ : c ∈ and f₁ f₂
hn' : ¬Valuation.satisfies v c
h : c ∈ f₁
⊢ False
[PROOFSTEP]
exact hn $ Or.inl $ h₁.1 fun Hc ↦ hn' $ Hc.1 _ h
[GOAL]
case inr
v : Valuation
f₁ : Fmla
a : Prop
f₂ : Fmla
b : Prop
h₁ : reify v f₁ a
h₂ : reify v f₂ b
H : ¬Valuation.satisfies_fmla v (and f₁ f₂)
hn : ¬(a ∨ b)
c : Clause
h✝ : c ∈ and f₁ f₂
hn' : ¬Valuation.satisfies v c
h : c ∈ f₂
⊢ False
[PROOFSTEP]
exact hn $ Or.inr $ h₂.1 fun Hc ↦ hn' $ Hc.1 _ h


[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
x : Multiset α × Multiset α
l : List α
⊢ x ∈ antidiagonal (Quotient.mk (isSetoid α) l) ↔ x.fst + x.snd = Quotient.mk (isSetoid α) l
[PROOFSTEP]
dsimp only [quot_mk_to_coe, antidiagonal_coe]
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
x : Multiset α × Multiset α
l : List α
⊢ x ∈ ↑(revzip (powersetAux l)) ↔ x.fst + x.snd = ↑l
[PROOFSTEP]
refine' ⟨fun h => revzip_powersetAux h, fun h ↦ _⟩
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
x : Multiset α × Multiset α
l : List α
h : x.fst + x.snd = ↑l
⊢ x ∈ ↑(revzip (powersetAux l))
[PROOFSTEP]
haveI := Classical.decEq α
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
x : Multiset α × Multiset α
l : List α
h : x.fst + x.snd = ↑l
this : DecidableEq α
⊢ x ∈ ↑(revzip (powersetAux l))
[PROOFSTEP]
simp only [revzip_powersetAux_lemma l revzip_powersetAux, h.symm, ge_iff_le, mem_coe, List.mem_map, mem_powersetAux]
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
x : Multiset α × Multiset α
l : List α
h : x.fst + x.snd = ↑l
this : DecidableEq α
⊢ ∃ a, a ≤ x.fst + x.snd ∧ (a, x.fst + x.snd - a) = x
[PROOFSTEP]
cases' x with x₁ x₂
[GOAL]
case mk
α : Type u_1
β : Type u_2
s : Multiset α
l : List α
this : DecidableEq α
x₁ x₂ : Multiset α
h : (x₁, x₂).fst + (x₁, x₂).snd = ↑l
⊢ ∃ a, a ≤ (x₁, x₂).fst + (x₁, x₂).snd ∧ (a, (x₁, x₂).fst + (x₁, x₂).snd - a) = (x₁, x₂)
[PROOFSTEP]
exact ⟨x₁, le_add_right _ _, by rw [add_tsub_cancel_left x₁ x₂]⟩
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
l : List α
this : DecidableEq α
x₁ x₂ : Multiset α
h : (x₁, x₂).fst + (x₁, x₂).snd = ↑l
⊢ (x₁, (x₁, x₂).fst + (x₁, x₂).snd - x₁) = (x₁, x₂)
[PROOFSTEP]
rw [add_tsub_cancel_left x₁ x₂]
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
l : List α
⊢ map Prod.fst (antidiagonal (Quotient.mk (isSetoid α) l)) = powerset (Quotient.mk (isSetoid α) l)
[PROOFSTEP]
simp [powersetAux']
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
l : List α
⊢ map Prod.snd (antidiagonal (Quotient.mk (isSetoid α) l)) = powerset (Quotient.mk (isSetoid α) l)
[PROOFSTEP]
simp [powersetAux']
[GOAL]
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ antidiagonal (a ::ₘ Quotient.mk (isSetoid α) l) =
    map (Prod.map id (cons a)) (antidiagonal (Quotient.mk (isSetoid α) l)) +
      map (Prod.map (cons a) id) (antidiagonal (Quotient.mk (isSetoid α) l))
[PROOFSTEP]
simp only [revzip, reverse_append, quot_mk_to_coe, coe_eq_coe, powersetAux'_cons, cons_coe, coe_map, antidiagonal_coe',
  coe_add]
[GOAL]
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ zip (powersetAux' l ++ List.map (cons a) (powersetAux' l))
      (reverse (List.map (cons a) (powersetAux' l)) ++ reverse (powersetAux' l)) ~
    List.map (fun x => Prod.map id (cons a) x) (zip (powersetAux' l) (reverse (powersetAux' l))) ++
      List.map (fun x => Prod.map (cons a) id x) (zip (powersetAux' l) (reverse (powersetAux' l)))
[PROOFSTEP]
rw [← zip_map, ← zip_map, zip_append, (_ : _ ++ _ = _)]
[GOAL]
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ zip (powersetAux' l) (reverse (List.map (cons a) (powersetAux' l))) ++
      zip (List.map (cons a) (powersetAux' l)) (reverse (powersetAux' l)) =
    zip (List.map id (powersetAux' l)) (List.map (cons a) (reverse (powersetAux' l))) ++
      zip (List.map (cons a) (powersetAux' l)) (List.map id (reverse (powersetAux' l)))
[PROOFSTEP]
congr
[GOAL]
case e_a.e_a
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ powersetAux' l = List.map id (powersetAux' l)
case e_a.e_a
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ reverse (List.map (cons a) (powersetAux' l)) = List.map (cons a) (reverse (powersetAux' l))
case e_a.e_a
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ reverse (powersetAux' l) = List.map id (reverse (powersetAux' l))
[PROOFSTEP]
simp
[GOAL]
case e_a.e_a
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ reverse (List.map (cons a) (powersetAux' l)) = List.map (cons a) (reverse (powersetAux' l))
case e_a.e_a
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ reverse (powersetAux' l) = List.map id (reverse (powersetAux' l))
[PROOFSTEP]
rw [map_reverse]
[GOAL]
case e_a.e_a
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ reverse (powersetAux' l) = List.map id (reverse (powersetAux' l))
[PROOFSTEP]
simp
[GOAL]
α : Type u_1
β : Type u_2
a : α
s : Multiset α
l : List α
⊢ length (powersetAux' l) = length (reverse (List.map (cons a) (powersetAux' l)))
[PROOFSTEP]
simp
[GOAL]
α : Type u_1
β : Type u_2
inst✝ : DecidableEq α
s : Multiset α
⊢ antidiagonal s = map (fun t => (s - t, t)) (powerset s)
[PROOFSTEP]
induction' s using Multiset.induction_on with a s hs
[GOAL]
case empty
α : Type u_1
β : Type u_2
inst✝ : DecidableEq α
⊢ antidiagonal 0 = map (fun t => (0 - t, t)) (powerset 0)
[PROOFSTEP]
simp only [antidiagonal_zero, powerset_zero, zero_tsub, map_singleton]
[GOAL]
case cons
α : Type u_1
β : Type u_2
inst✝ : DecidableEq α
a : α
s : Multiset α
hs : antidiagonal s = map (fun t => (s - t, t)) (powerset s)
⊢ antidiagonal (a ::ₘ s) = map (fun t => (a ::ₘ s - t, t)) (powerset (a ::ₘ s))
[PROOFSTEP]
simp_rw [antidiagonal_cons, powerset_cons, map_add, hs, map_map, Function.comp, Prod.map_mk, id.def, sub_cons,
  erase_cons_head]
[GOAL]
case cons
α : Type u_1
β : Type u_2
inst✝ : DecidableEq α
a : α
s : Multiset α
hs : antidiagonal s = map (fun t => (s - t, t)) (powerset s)
⊢ map (fun x => (s - x, a ::ₘ x)) (powerset s) + map (fun x => (a ::ₘ (s - x), x)) (powerset s) =
    map (fun x => (a ::ₘ s - x, x)) (powerset s) + map (fun x => (s - x, a ::ₘ x)) (powerset s)
[PROOFSTEP]
rw [add_comm]
[GOAL]
case cons
α : Type u_1
β : Type u_2
inst✝ : DecidableEq α
a : α
s : Multiset α
hs : antidiagonal s = map (fun t => (s - t, t)) (powerset s)
⊢ map (fun x => (a ::ₘ (s - x), x)) (powerset s) + map (fun x => (s - x, a ::ₘ x)) (powerset s) =
    map (fun x => (a ::ₘ s - x, x)) (powerset s) + map (fun x => (s - x, a ::ₘ x)) (powerset s)
[PROOFSTEP]
congr 1
[GOAL]
case cons.e_a
α : Type u_1
β : Type u_2
inst✝ : DecidableEq α
a : α
s : Multiset α
hs : antidiagonal s = map (fun t => (s - t, t)) (powerset s)
⊢ map (fun x => (a ::ₘ (s - x), x)) (powerset s) = map (fun x => (a ::ₘ s - x, x)) (powerset s)
[PROOFSTEP]
refine' Multiset.map_congr rfl fun x hx ↦ _
[GOAL]
case cons.e_a
α : Type u_1
β : Type u_2
inst✝ : DecidableEq α
a : α
s : Multiset α
hs : antidiagonal s = map (fun t => (s - t, t)) (powerset s)
x : Multiset α
hx : x ∈ powerset s
⊢ (a ::ₘ (s - x), x) = (a ::ₘ s - x, x)
[PROOFSTEP]
rw [cons_sub_of_le _ (mem_powerset.mp hx)]
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
⊢ ↑card (antidiagonal s) = 2 ^ ↑card s
[PROOFSTEP]
have := card_powerset s
[GOAL]
α : Type u_1
β : Type u_2
s : Multiset α
this : ↑card (powerset s) = 2 ^ ↑card s
⊢ ↑card (antidiagonal s) = 2 ^ ↑card s
[PROOFSTEP]
rwa [← antidiagonal_map_fst, card_map] at this
[GOAL]
α : Type u_1
β : Type u_2
inst✝ : CommSemiring β
s : Multiset α
f g : α → β
⊢ prod (map (fun a => f a + g a) s) = sum (map (fun p => prod (map f p.fst) * prod (map g p.snd)) (antidiagonal s))
[PROOFSTEP]
refine' s.induction_on _ _
[GOAL]
case refine'_1
α : Type u_1
β : Type u_2
inst✝ : CommSemiring β
s : Multiset α
f g : α → β
⊢ prod (map (fun a => f a + g a) 0) = sum (map (fun p => prod (map f p.fst) * prod (map g p.snd)) (antidiagonal 0))
[PROOFSTEP]
simp only [map_zero, prod_zero, antidiagonal_zero, map_singleton, mul_one, sum_singleton]
[GOAL]
case refine'_2
α : Type u_1
β : Type u_2
inst✝ : CommSemiring β
s : Multiset α
f g : α → β
⊢ ∀ ⦃a : α⦄ {s : Multiset α},
    prod (map (fun a => f a + g a) s) = sum (map (fun p => prod (map f p.fst) * prod (map g p.snd)) (antidiagonal s)) →
      prod (map (fun a => f a + g a) (a ::ₘ s)) =
        sum (map (fun p => prod (map f p.fst) * prod (map g p.snd)) (antidiagonal (a ::ₘ s)))
[PROOFSTEP]
intro a s ih
[GOAL]
case refine'_2
α : Type u_1
β : Type u_2
inst✝ : CommSemiring β
s✝ : Multiset α
f g : α → β
a : α
s : Multiset α
ih : prod (map (fun a => f a + g a) s) = sum (map (fun p => prod (map f p.fst) * prod (map g p.snd)) (antidiagonal s))
⊢ prod (map (fun a => f a + g a) (a ::ₘ s)) =
    sum (map (fun p => prod (map f p.fst) * prod (map g p.snd)) (antidiagonal (a ::ₘ s)))
[PROOFSTEP]
simp only [map_cons, prod_cons, ih, sum_map_mul_left.symm, add_mul, mul_left_comm (f a), mul_left_comm (g a),
  sum_map_add, antidiagonal_cons, Prod_map, id_eq, map_add, map_map, Function.comp_apply, mul_assoc, sum_add]
[GOAL]
case refine'_2
α : Type u_1
β : Type u_2
inst✝ : CommSemiring β
s✝ : Multiset α
f g : α → β
a : α
s : Multiset α
ih : prod (map (fun a => f a + g a) s) = sum (map (fun p => prod (map f p.fst) * prod (map g p.snd)) (antidiagonal s))
⊢ sum (map (fun i => prod (map f i.fst) * (f a * prod (map g i.snd))) (antidiagonal s)) +
      sum (map (fun i => prod (map f i.fst) * (g a * prod (map g i.snd))) (antidiagonal s)) =
    sum (map (fun x => prod (map f x.fst) * (g a * prod (map g x.snd))) (antidiagonal s)) +
      sum (map (fun i => prod (map f i.fst) * (f a * prod (map g i.snd))) (antidiagonal s))
[PROOFSTEP]
exact add_comm _ _