l3lab/ntp-mathlib huggingface dataset:
instance fintypeEdgeSetSdiff [DecidableEq V] [Fintype G₁.edgeSet] [Fintype G₂.edgeSet] :
    Fintype (G₁ \ G₂).edgeSet := by
  rw [edgeSet_sdiff]
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
G₁ G₂ : SimpleGraph V
inst✝² : DecidableEq V
inst✝¹ : Fintype ↑(edgeSet G₁)
inst✝ : Fintype ↑(edgeSet G₂)
⊢ Fintype ↑(edgeSet G₁ \ edgeSet G₂)

Next tactic:
exact Set.fintypeDiff _ _
@[simp]
theorem edgeSet_fromEdgeSet : (fromEdgeSet s).edgeSet = s \ { e | e.IsDiag } := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ edgeSet (fromEdgeSet s) = s \ {e | Sym2.IsDiag e}

Next tactic:
ext e
@[simp]
theorem edgeSet_fromEdgeSet : (fromEdgeSet s).edgeSet = s \ { e | e.IsDiag } := by
  ext e
  

Proof state:
case h
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e✝ : Sym2 V
s : Set (Sym2 V)
e : Sym2 V
⊢ e ∈ edgeSet (fromEdgeSet s) ↔ e ∈ s \ {e | Sym2.IsDiag e}

Next tactic:
exact Sym2.ind (by simp) e
@[simp]
theorem edgeSet_fromEdgeSet : (fromEdgeSet s).edgeSet = s \ { e | e.IsDiag } := by
  ext e
  exact Sym2.ind (by 

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e✝ : Sym2 V
s : Set (Sym2 V)
e : Sym2 V
⊢ ∀ (x y : V), ⟦(x, y)⟧ ∈ edgeSet (fromEdgeSet s) ↔ ⟦(x, y)⟧ ∈ s \ {e | Sym2.IsDiag e}

Next tactic:
simp
@[simp]
theorem fromEdgeSet_edgeSet : fromEdgeSet G.edgeSet = G := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ fromEdgeSet (edgeSet G) = G

Next tactic:
ext v w
@[simp]
theorem fromEdgeSet_edgeSet : fromEdgeSet G.edgeSet = G := by
  ext v w
  

Proof state:
case Adj.h.h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet (edgeSet G)) v w ↔ Adj G v w

Next tactic:
exact ⟨fun h => h.1, fun h => ⟨h, G.ne_of_adj h⟩⟩
@[simp]
theorem fromEdgeSet_empty : fromEdgeSet (∅ : Set (Sym2 V)) = ⊥ := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ fromEdgeSet ∅ = ⊥

Next tactic:
ext v w
@[simp]
theorem fromEdgeSet_empty : fromEdgeSet (∅ : Set (Sym2 V)) = ⊥ := by
  ext v w
  

Proof state:
case Adj.h.h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet ∅) v w ↔ Adj ⊥ v w

Next tactic:
simp only [fromEdgeSet_adj, Set.mem_empty_iff_false, false_and_iff, bot_adj]
@[simp]
theorem fromEdgeSet_univ : fromEdgeSet (Set.univ : Set (Sym2 V)) = ⊤ := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ fromEdgeSet Set.univ = ⊤

Next tactic:
ext v w
@[simp]
theorem fromEdgeSet_univ : fromEdgeSet (Set.univ : Set (Sym2 V)) = ⊤ := by
  ext v w
  

Proof state:
case Adj.h.h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet Set.univ) v w ↔ Adj ⊤ v w

Next tactic:
simp only [fromEdgeSet_adj, Set.mem_univ, true_and_iff, top_adj]
@[simp]
theorem fromEdgeSet_inf (s t : Set (Sym2 V)) :
    fromEdgeSet s ⊓ fromEdgeSet t = fromEdgeSet (s ∩ t) := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
⊢ fromEdgeSet s ⊓ fromEdgeSet t = fromEdgeSet (s ∩ t)

Next tactic:
ext v w
@[simp]
theorem fromEdgeSet_inf (s t : Set (Sym2 V)) :
    fromEdgeSet s ⊓ fromEdgeSet t = fromEdgeSet (s ∩ t) := by
  ext v w
  

Proof state:
case Adj.h.h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet s ⊓ fromEdgeSet t) v w ↔ Adj (fromEdgeSet (s ∩ t)) v w

Next tactic:
simp only [fromEdgeSet_adj, Set.mem_inter_iff, Ne.def, inf_adj]
@[simp]
theorem fromEdgeSet_inf (s t : Set (Sym2 V)) :
    fromEdgeSet s ⊓ fromEdgeSet t = fromEdgeSet (s ∩ t) := by
  ext v w
  simp only [fromEdgeSet_adj, Set.mem_inter_iff, Ne.def, inf_adj]
  

Proof state:
case Adj.h.h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
v w : V
⊢ (⟦(v, w)⟧ ∈ s ∧ ¬v = w) ∧ ⟦(v, w)⟧ ∈ t ∧ ¬v = w ↔ (⟦(v, w)⟧ ∈ s ∧ ⟦(v, w)⟧ ∈ t) ∧ ¬v = w

Next tactic:
tauto
@[simp]
theorem fromEdgeSet_sup (s t : Set (Sym2 V)) :
    fromEdgeSet s ⊔ fromEdgeSet t = fromEdgeSet (s ∪ t) := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
⊢ fromEdgeSet s ⊔ fromEdgeSet t = fromEdgeSet (s ∪ t)

Next tactic:
ext v w
@[simp]
theorem fromEdgeSet_sup (s t : Set (Sym2 V)) :
    fromEdgeSet s ⊔ fromEdgeSet t = fromEdgeSet (s ∪ t) := by
  ext v w
  

Proof state:
case Adj.h.h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet s ⊔ fromEdgeSet t) v w ↔ Adj (fromEdgeSet (s ∪ t)) v w

Next tactic:
simp [Set.mem_union, or_and_right]
@[simp]
theorem fromEdgeSet_sdiff (s t : Set (Sym2 V)) :
    fromEdgeSet s \ fromEdgeSet t = fromEdgeSet (s \ t) := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
⊢ fromEdgeSet s \ fromEdgeSet t = fromEdgeSet (s \ t)

Next tactic:
ext v w
@[simp]
theorem fromEdgeSet_sdiff (s t : Set (Sym2 V)) :
    fromEdgeSet s \ fromEdgeSet t = fromEdgeSet (s \ t) := by
  ext v w
  

Proof state:
case Adj.h.h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet s \ fromEdgeSet t) v w ↔ Adj (fromEdgeSet (s \ t)) v w

Next tactic:
constructor
@[simp]
theorem fromEdgeSet_sdiff (s t : Set (Sym2 V)) :
    fromEdgeSet s \ fromEdgeSet t = fromEdgeSet (s \ t) := by
  ext v w
  constructor <;> 

Proof state:
case Adj.h.h.a.mp
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet s \ fromEdgeSet t) v w → Adj (fromEdgeSet (s \ t)) v w

Next tactic:
simp (config := { contextual := true })
@[simp]
theorem fromEdgeSet_sdiff (s t : Set (Sym2 V)) :
    fromEdgeSet s \ fromEdgeSet t = fromEdgeSet (s \ t) := by
  ext v w
  constructor <;> 

Proof state:
case Adj.h.h.a.mpr
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
v w : V
⊢ Adj (fromEdgeSet (s \ t)) v w → Adj (fromEdgeSet s \ fromEdgeSet t) v w

Next tactic:
simp (config := { contextual := true })
@[mono]
theorem fromEdgeSet_mono {s t : Set (Sym2 V)} (h : s ⊆ t) : fromEdgeSet s ≤ fromEdgeSet t := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
h : s ⊆ t
⊢ fromEdgeSet s ≤ fromEdgeSet t

Next tactic:
rintro v w
@[mono]
theorem fromEdgeSet_mono {s t : Set (Sym2 V)} (h : s ⊆ t) : fromEdgeSet s ≤ fromEdgeSet t := by
  rintro v w
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
h : s ⊆ t
v w : V
⊢ Adj (fromEdgeSet s) v w → Adj (fromEdgeSet t) v w

Next tactic:
simp (config := { contextual := true }) only [fromEdgeSet_adj, Ne.def, not_false_iff,
    and_true_iff, and_imp]
@[mono]
theorem fromEdgeSet_mono {s t : Set (Sym2 V)} (h : s ⊆ t) : fromEdgeSet s ≤ fromEdgeSet t := by
  rintro v w
  simp (config := { contextual := true }) only [fromEdgeSet_adj, Ne.def, not_false_iff,
    and_true_iff, and_imp]
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
s✝ s t : Set (Sym2 V)
h : s ⊆ t
v w : V
⊢ ⟦(v, w)⟧ ∈ s → ¬v = w → ⟦(v, w)⟧ ∈ t

Next tactic:
exact fun vws _ => h vws
@[simp] lemma disjoint_fromEdgeSet : Disjoint G (fromEdgeSet s) ↔ Disjoint G.edgeSet s := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ Disjoint G (fromEdgeSet s) ↔ Disjoint (edgeSet G) s

Next tactic:
conv_rhs => rw [← Set.diff_union_inter s {e : Sym2 V | e.IsDiag}]
@[simp] lemma disjoint_fromEdgeSet : Disjoint G (fromEdgeSet s) ↔ Disjoint G.edgeSet s := by
  conv_rhs => 

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
| Disjoint (edgeSet G) s

Next tactic:
rw [← Set.diff_union_inter s {e : Sym2 V | e.IsDiag}]
@[simp] lemma disjoint_fromEdgeSet : Disjoint G (fromEdgeSet s) ↔ Disjoint G.edgeSet s := by
  conv_rhs => rw [← Set.diff_union_inter s {e : Sym2 V | e.IsDiag}]
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ Disjoint G (fromEdgeSet s) ↔ Disjoint (edgeSet G) (s \ {e | Sym2.IsDiag e} ∪ s ∩ {e | Sym2.IsDiag e})

Next tactic:
rw [← disjoint_edgeSet,  edgeSet_fromEdgeSet, Set.disjoint_union_right, and_iff_left]
@[simp] lemma disjoint_fromEdgeSet : Disjoint G (fromEdgeSet s) ↔ Disjoint G.edgeSet s := by
  conv_rhs => rw [← Set.diff_union_inter s {e : Sym2 V | e.IsDiag}]
  rw [← disjoint_edgeSet,  edgeSet_fromEdgeSet, Set.disjoint_union_right, and_iff_left]
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ Disjoint (edgeSet G) (s ∩ {e | Sym2.IsDiag e})

Next tactic:
exact Set.disjoint_left.2 fun e he he' ↦ not_isDiag_of_mem_edgeSet _ he he'.2
@[simp] lemma fromEdgeSet_disjoint : Disjoint (fromEdgeSet s) G ↔ Disjoint s G.edgeSet := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
⊢ Disjoint (fromEdgeSet s) G ↔ Disjoint s (edgeSet G)

Next tactic:
rw [disjoint_comm, disjoint_fromEdgeSet, disjoint_comm]
instance [DecidableEq V] [Fintype s] : Fintype (fromEdgeSet s).edgeSet := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
inst✝¹ : DecidableEq V
inst✝ : Fintype ↑s
⊢ Fintype ↑(edgeSet (fromEdgeSet s))

Next tactic:
rw [edgeSet_fromEdgeSet s]
instance [DecidableEq V] [Fintype s] : Fintype (fromEdgeSet s).edgeSet := by
  rw [edgeSet_fromEdgeSet s]
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
s : Set (Sym2 V)
inst✝¹ : DecidableEq V
inst✝ : Fintype ↑s
⊢ Fintype ↑(s \ {e | Sym2.IsDiag e})

Next tactic:
infer_instance
theorem Dart.ext_iff (d₁ d₂ : G.Dart) : d₁ = d₂ ↔ d₁.toProd = d₂.toProd := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
d₁ d₂ : Dart G
⊢ d₁ = d₂ ↔ d₁.toProd = d₂.toProd

Next tactic:
cases d₁
theorem Dart.ext_iff (d₁ d₂ : G.Dart) : d₁ = d₂ ↔ d₁.toProd = d₂.toProd := by
  cases d₁; 

Proof state:
case mk
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
d₂ : Dart G
toProd✝ : V × V
is_adj✝ : Adj G toProd✝.1 toProd✝.2
⊢ { toProd := toProd✝, is_adj := is_adj✝ } = d₂ ↔ { toProd := toProd✝, is_adj := is_adj✝ }.toProd = d₂.toProd

Next tactic:
cases d₂
theorem Dart.ext_iff (d₁ d₂ : G.Dart) : d₁ = d₂ ↔ d₁.toProd = d₂.toProd := by
  cases d₁; cases d₂; 

Proof state:
case mk.mk
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
toProd✝¹ : V × V
is_adj✝¹ : Adj G toProd✝¹.1 toProd✝¹.2
toProd✝ : V × V
is_adj✝ : Adj G toProd✝.1 toProd✝.2
⊢ { toProd := toProd✝¹, is_adj := is_adj✝¹ } = { toProd := toProd✝, is_adj := is_adj✝ } ↔
    { toProd := toProd✝¹, is_adj := is_adj✝¹ }.toProd = { toProd := toProd✝, is_adj := is_adj✝ }.toProd

Next tactic:
simp
instance Dart.fintype [Fintype V] [DecidableRel G.Adj] : Fintype G.Dart :=
  Fintype.ofEquiv (Σ v, G.neighborSet v)
    { toFun := fun s => ⟨(s.fst, s.snd), s.snd.property⟩
      invFun := fun d => ⟨d.fst, d.snd, d.is_adj⟩
      left_inv := fun s => by 

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
inst✝¹ : Fintype V
inst✝ : DecidableRel G.Adj
s : (v : V) × ↑(neighborSet G v)
⊢ (fun d => { fst := d.toProd.1, snd := { val := d.toProd.2, property := (_ : Adj G d.toProd.1 d.toProd.2) } })
      ((fun s => { toProd := (s.fst, ↑s.snd), is_adj := (_ : ↑s.snd ∈ neighborSet G s.fst) }) s) =
    s

Next tactic:
ext
instance Dart.fintype [Fintype V] [DecidableRel G.Adj] : Fintype G.Dart :=
  Fintype.ofEquiv (Σ v, G.neighborSet v)
    { toFun := fun s => ⟨(s.fst, s.snd), s.snd.property⟩
      invFun := fun d => ⟨d.fst, d.snd, d.is_adj⟩
      left_inv := fun s => by ext <;> 

Proof state:
case a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
inst✝¹ : Fintype V
inst✝ : DecidableRel G.Adj
s : (v : V) × ↑(neighborSet G v)
⊢ ((fun d => { fst := d.toProd.1, snd := { val := d.toProd.2, property := (_ : Adj G d.toProd.1 d.toProd.2) } })
        ((fun s => { toProd := (s.fst, ↑s.snd), is_adj := (_ : ↑s.snd ∈ neighborSet G s.fst) }) s)).fst =
    s.fst

Next tactic:
simp
instance Dart.fintype [Fintype V] [DecidableRel G.Adj] : Fintype G.Dart :=
  Fintype.ofEquiv (Σ v, G.neighborSet v)
    { toFun := fun s => ⟨(s.fst, s.snd), s.snd.property⟩
      invFun := fun d => ⟨d.fst, d.snd, d.is_adj⟩
      left_inv := fun s => by ext <;> 

Proof state:
case a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
inst✝¹ : Fintype V
inst✝ : DecidableRel G.Adj
s : (v : V) × ↑(neighborSet G v)
⊢ ↑((fun d => { fst := d.toProd.1, snd := { val := d.toProd.2, property := (_ : Adj G d.toProd.1 d.toProd.2) } })
          ((fun s => { toProd := (s.fst, ↑s.snd), is_adj := (_ : ↑s.snd ∈ neighborSet G s.fst) }) s)).snd =
    ↑s.snd

Next tactic:
simp
instance Dart.fintype [Fintype V] [DecidableRel G.Adj] : Fintype G.Dart :=
  Fintype.ofEquiv (Σ v, G.neighborSet v)
    { toFun := fun s => ⟨(s.fst, s.snd), s.snd.property⟩
      invFun := fun d => ⟨d.fst, d.snd, d.is_adj⟩
      left_inv := fun s => by ext <;> simp
      right_inv := fun d => by 

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
inst✝¹ : Fintype V
inst✝ : DecidableRel G.Adj
d : Dart G
⊢ (fun s => { toProd := (s.fst, ↑s.snd), is_adj := (_ : ↑s.snd ∈ neighborSet G s.fst) })
      ((fun d => { fst := d.toProd.1, snd := { val := d.toProd.2, property := (_ : Adj G d.toProd.1 d.toProd.2) } })
        d) =
    d

Next tactic:
ext
instance Dart.fintype [Fintype V] [DecidableRel G.Adj] : Fintype G.Dart :=
  Fintype.ofEquiv (Σ v, G.neighborSet v)
    { toFun := fun s => ⟨(s.fst, s.snd), s.snd.property⟩
      invFun := fun d => ⟨d.fst, d.snd, d.is_adj⟩
      left_inv := fun s => by ext <;> simp
      right_inv := fun d => by ext <;> 

Proof state:
case h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
inst✝¹ : Fintype V
inst✝ : DecidableRel G.Adj
d : Dart G
⊢ ((fun s => { toProd := (s.fst, ↑s.snd), is_adj := (_ : ↑s.snd ∈ neighborSet G s.fst) })
          ((fun d => { fst := d.toProd.1, snd := { val := d.toProd.2, property := (_ : Adj G d.toProd.1 d.toProd.2) } })
            d)).toProd.1 =
    d.toProd.1

Next tactic:
simp
instance Dart.fintype [Fintype V] [DecidableRel G.Adj] : Fintype G.Dart :=
  Fintype.ofEquiv (Σ v, G.neighborSet v)
    { toFun := fun s => ⟨(s.fst, s.snd), s.snd.property⟩
      invFun := fun d => ⟨d.fst, d.snd, d.is_adj⟩
      left_inv := fun s => by ext <;> simp
      right_inv := fun d => by ext <;> 

Proof state:
case h.a
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
inst✝¹ : Fintype V
inst✝ : DecidableRel G.Adj
d : Dart G
⊢ ((fun s => { toProd := (s.fst, ↑s.snd), is_adj := (_ : ↑s.snd ∈ neighborSet G s.fst) })
          ((fun d => { fst := d.toProd.1, snd := { val := d.toProd.2, property := (_ : Adj G d.toProd.1 d.toProd.2) } })
            d)).toProd.2 =
    d.toProd.2

Next tactic:
simp
theorem dart_edge_eq_iff : ∀ d₁ d₂ : G.Dart, d₁.edge = d₂.edge ↔ d₁ = d₂ ∨ d₁ = d₂.symm := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
⊢ ∀ (d₁ d₂ : Dart G), Dart.edge d₁ = Dart.edge d₂ ↔ d₁ = d₂ ∨ d₁ = Dart.symm d₂

Next tactic:
rintro ⟨p, hp⟩ ⟨q, hq⟩
theorem dart_edge_eq_iff : ∀ d₁ d₂ : G.Dart, d₁.edge = d₂.edge ↔ d₁ = d₂ ∨ d₁ = d₂.symm := by
  rintro ⟨p, hp⟩ ⟨q, hq⟩
  

Proof state:
case mk.mk
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
p : V × V
hp : Adj G p.1 p.2
q : V × V
hq : Adj G q.1 q.2
⊢ Dart.edge { toProd := p, is_adj := hp } = Dart.edge { toProd := q, is_adj := hq } ↔
    { toProd := p, is_adj := hp } = { toProd := q, is_adj := hq } ∨
      { toProd := p, is_adj := hp } = Dart.symm { toProd := q, is_adj := hq }

Next tactic:
simp [Sym2.mk''_eq_mk''_iff, -Quotient.eq]
theorem dart_edge_eq_mk'_iff :
    ∀ {d : G.Dart} {p : V × V}, d.edge = ⟦p⟧ ↔ d.toProd = p ∨ d.toProd = p.swap := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
⊢ ∀ {d : Dart G} {p : V × V}, Dart.edge d = ⟦p⟧ ↔ d.toProd = p ∨ d.toProd = Prod.swap p

Next tactic:
rintro ⟨p, h⟩
theorem dart_edge_eq_mk'_iff :
    ∀ {d : G.Dart} {p : V × V}, d.edge = ⟦p⟧ ↔ d.toProd = p ∨ d.toProd = p.swap := by
  rintro ⟨p, h⟩
  

Proof state:
case mk
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
p : V × V
h : Adj G p.1 p.2
⊢ ∀ {p_1 : V × V},
    Dart.edge { toProd := p, is_adj := h } = ⟦p_1⟧ ↔
      { toProd := p, is_adj := h }.toProd = p_1 ∨ { toProd := p, is_adj := h }.toProd = Prod.swap p_1

Next tactic:
apply Sym2.mk''_eq_mk''_iff
theorem dart_edge_eq_mk'_iff' :
    ∀ {d : G.Dart} {u v : V},
      d.edge = ⟦(u, v)⟧ ↔ d.fst = u ∧ d.snd = v ∨ d.fst = v ∧ d.snd = u := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
⊢ ∀ {d : Dart G} {u v : V}, Dart.edge d = ⟦(u, v)⟧ ↔ d.toProd.1 = u ∧ d.toProd.2 = v ∨ d.toProd.1 = v ∧ d.toProd.2 = u

Next tactic:
rintro ⟨⟨a, b⟩, h⟩ u v
theorem dart_edge_eq_mk'_iff' :
    ∀ {d : G.Dart} {u v : V},
      d.edge = ⟦(u, v)⟧ ↔ d.fst = u ∧ d.snd = v ∨ d.fst = v ∧ d.snd = u := by
  rintro ⟨⟨a, b⟩, h⟩ u v
  

Proof state:
case mk.mk
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a✝ b✝ c u✝ v✝ w : V
e : Sym2 V
a b : V
h : Adj G (a, b).1 (a, b).2
u v : V
⊢ Dart.edge { toProd := (a, b), is_adj := h } = ⟦(u, v)⟧ ↔
    { toProd := (a, b), is_adj := h }.toProd.1 = u ∧ { toProd := (a, b), is_adj := h }.toProd.2 = v ∨
      { toProd := (a, b), is_adj := h }.toProd.1 = v ∧ { toProd := (a, b), is_adj := h }.toProd.2 = u

Next tactic:
rw [dart_edge_eq_mk'_iff]
theorem dart_edge_eq_mk'_iff' :
    ∀ {d : G.Dart} {u v : V},
      d.edge = ⟦(u, v)⟧ ↔ d.fst = u ∧ d.snd = v ∨ d.fst = v ∧ d.snd = u := by
  rintro ⟨⟨a, b⟩, h⟩ u v
  rw [dart_edge_eq_mk'_iff]
  

Proof state:
case mk.mk
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a✝ b✝ c u✝ v✝ w : V
e : Sym2 V
a b : V
h : Adj G (a, b).1 (a, b).2
u v : V
⊢ { toProd := (a, b), is_adj := h }.toProd = (u, v) ∨ { toProd := (a, b), is_adj := h }.toProd = Prod.swap (u, v) ↔
    { toProd := (a, b), is_adj := h }.toProd.1 = u ∧ { toProd := (a, b), is_adj := h }.toProd.2 = v ∨
      { toProd := (a, b), is_adj := h }.toProd.1 = v ∧ { toProd := (a, b), is_adj := h }.toProd.2 = u

Next tactic:
simp
theorem dartOfNeighborSet_injective (v : V) : Function.Injective (G.dartOfNeighborSet v) :=
  fun e₁ e₂ h =>
  Subtype.ext <| by
    

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w : V
e : Sym2 V
v : V
e₁ e₂ : ↑(neighborSet G v)
h : dartOfNeighborSet G v e₁ = dartOfNeighborSet G v e₂
⊢ ↑e₁ = ↑e₂

Next tactic:
injection h with h'
theorem dartOfNeighborSet_injective (v : V) : Function.Injective (G.dartOfNeighborSet v) :=
  fun e₁ e₂ h =>
  Subtype.ext <| by
    injection h with h'
    

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w : V
e : Sym2 V
v : V
e₁ e₂ : ↑(neighborSet G v)
h' : (v, ↑e₁) = (v, ↑e₂)
⊢ ↑e₁ = ↑e₂

Next tactic:
convert congr_arg Prod.snd h'
instance nonempty_dart_top [Nontrivial V] : Nonempty (⊤ : SimpleGraph V).Dart := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
inst✝ : Nontrivial V
⊢ Nonempty (Dart ⊤)

Next tactic:
obtain ⟨v, w, h⟩ := exists_pair_ne V
instance nonempty_dart_top [Nontrivial V] : Nonempty (⊤ : SimpleGraph V).Dart := by
  obtain ⟨v, w, h⟩ := exists_pair_ne V
  

Proof state:
case intro.intro
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v✝ w✝ : V
e : Sym2 V
inst✝ : Nontrivial V
v w : V
h : v ≠ w
⊢ Nonempty (Dart ⊤)

Next tactic:
exact ⟨⟨(v, w), h⟩⟩
theorem incidenceSet_inter_incidenceSet_of_adj (h : G.Adj a b) :
    G.incidenceSet a ∩ G.incidenceSet b = {⟦(a, b)⟧} := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
h : Adj G a b
⊢ incidenceSet G a ∩ incidenceSet G b = {⟦(a, b)⟧}

Next tactic:
refine' (G.incidenceSet_inter_incidenceSet_subset <| h.ne).antisymm _
theorem incidenceSet_inter_incidenceSet_of_adj (h : G.Adj a b) :
    G.incidenceSet a ∩ G.incidenceSet b = {⟦(a, b)⟧} := by
  refine' (G.incidenceSet_inter_incidenceSet_subset <| h.ne).antisymm _
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
h : Adj G a b
⊢ {⟦(a, b)⟧} ⊆ incidenceSet G a ∩ incidenceSet G b

Next tactic:
rintro _ (rfl : _ = ⟦(a, b)⟧)
theorem incidenceSet_inter_incidenceSet_of_adj (h : G.Adj a b) :
    G.incidenceSet a ∩ G.incidenceSet b = {⟦(a, b)⟧} := by
  refine' (G.incidenceSet_inter_incidenceSet_subset <| h.ne).antisymm _
  rintro _ (rfl : _ = ⟦(a, b)⟧)
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
h : Adj G a b
⊢ ⟦(a, b)⟧ ∈ incidenceSet G a ∩ incidenceSet G b

Next tactic:
exact ⟨G.mk'_mem_incidenceSet_left_iff.2 h, G.mk'_mem_incidenceSet_right_iff.2 h⟩
theorem adj_of_mem_incidenceSet (h : a ≠ b) (ha : e ∈ G.incidenceSet a)
    (hb : e ∈ G.incidenceSet b) : G.Adj a b := by
  

Proof state:
ι : Sort u_1
𝕜 : Type u_2
V : Type u
W : Type v
X : Type w
G : SimpleGraph V
G' : SimpleGraph W
a b c u v w : V
e : Sym2 V
h : a ≠ b
ha : e ∈ incidenceSet G a
hb : e ∈ incidenceSet G b
⊢ Adj G a b

Next tactic:
rwa [← mk'_mem_incidenceSet_left_iff, ←
    Set.mem_singleton_iff.1 <| G.incidenceSet_inter_incidenceSet_subset h ⟨ha, hb⟩]