field_theory.finite.basicMathlib.FieldTheory.Finite.Basic

This file has been ported!

Changes since the initial port

The following section lists changes to this file in mathlib3 and mathlib4 that occured after the initial port. Most recent changes are shown first. Hovering over a commit will show all commits associated with the same mathlib3 commit.

Changes in mathlib3

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(no changes)

(last sync)

Changes in mathlib3port

mathlib3
mathlib3port
Diff
@@ -516,10 +516,10 @@ theorem Int.ModEq.pow_card_sub_one_eq_one {p : ℕ} (hp : Nat.Prime p) {n : ℤ}
   haveI : Fact p.prime := ⟨hp⟩
   have : ¬(n : ZMod p) = 0 :=
     by
-    rw [CharP.int_cast_eq_zero_iff _ p, ← (nat.prime_iff_prime_int.mp hp).coprime_iff_not_dvd]
+    rw [CharP.intCast_eq_zero_iff _ p, ← (nat.prime_iff_prime_int.mp hp).coprime_iff_not_dvd]
     · exact hpn.symm
     exact ZMod.charP p
-  simpa [← ZMod.int_cast_eq_int_cast_iff] using ZMod.pow_card_sub_one_eq_one this
+  simpa [← ZMod.intCast_eq_intCast_iff] using ZMod.pow_card_sub_one_eq_one this
 #align int.modeq.pow_card_sub_one_eq_one Int.ModEq.pow_card_sub_one_eq_one
 -/
 
Diff
@@ -143,7 +143,7 @@ theorem pow_card (a : K) : a ^ q = a :=
   by
   have hp : 0 < Fintype.card K := lt_trans zero_lt_one Fintype.one_lt_card
   by_cases h : a = 0; · rw [h]; apply zero_pow hp
-  rw [← Nat.succ_pred_eq_of_pos hp, pow_succ, Nat.pred_eq_sub_one, pow_card_sub_one_eq_one a h,
+  rw [← Nat.succ_pred_eq_of_pos hp, pow_succ', Nat.pred_eq_sub_one, pow_card_sub_one_eq_one a h,
     mul_one]
 #align finite_field.pow_card FiniteField.pow_card
 -/
@@ -153,7 +153,7 @@ theorem pow_card_pow (n : ℕ) (a : K) : a ^ q ^ n = a :=
   by
   induction' n with n ih
   · simp
-  · simp [pow_succ, pow_mul, ih, pow_card]
+  · simp [pow_succ', pow_mul, ih, pow_card]
 #align finite_field.pow_card_pow FiniteField.pow_card_pow
 -/
 
@@ -331,7 +331,7 @@ theorem frobenius_pow {p : ℕ} [Fact p.Prime] [CharP K p] {n : ℕ} (hcard : q
     frobenius K p ^ n = 1 := by
   ext; conv_rhs => rw [RingHom.one_def, RingHom.id_apply, ← pow_card x, hcard]; clear hcard
   induction n; · simp
-  rw [pow_succ, pow_succ', pow_mul, RingHom.mul_def, RingHom.comp_apply, frobenius_def, n_ih]
+  rw [pow_succ', pow_succ, pow_mul, RingHom.mul_def, RingHom.comp_apply, frobenius_def, n_ih]
 #align finite_field.frobenius_pow FiniteField.frobenius_pow
 -/
 
@@ -453,7 +453,7 @@ theorem pow_card_pow {n p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p ^ n = x :=
   by
   induction' n with n ih
   · simp
-  · simp [pow_succ, pow_mul, ih, pow_card]
+  · simp [pow_succ', pow_mul, ih, pow_card]
 #align zmod.pow_card_pow ZMod.pow_card_pow
 -/
 
Diff
@@ -83,8 +83,8 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
   letI := Classical.decEq R
   suffices ¬Disjoint (univ.image fun x : R => eval x f) (univ.image fun x : R => eval x (-g))
     by
-    simp only [disjoint_left, mem_image] at this 
-    push_neg at this 
+    simp only [disjoint_left, mem_image] at this
+    push_neg at this
     rcases this with ⟨x, ⟨a, _, ha⟩, ⟨b, _, hb⟩⟩
     exact ⟨a, b, by rw [ha, ← hb, eval_neg, neg_add_self]⟩
   fun hd : Disjoint _ _ =>
@@ -167,11 +167,11 @@ theorem card (p : ℕ) [CharP K p] : ∃ n : ℕ+, Nat.Prime p ∧ q = p ^ (n :
   haveI hp : Fact p.prime := ⟨CharP.char_is_prime K p⟩
   letI : Module (ZMod p) K := { (ZMod.castHom dvd_rfl K : ZMod p →+* _).toModule with }
   obtain ⟨n, h⟩ := VectorSpace.card_fintype (ZMod p) K
-  rw [ZMod.card] at h 
+  rw [ZMod.card] at h
   refine' ⟨⟨n, _⟩, hp.1, h⟩
   apply Or.resolve_left (Nat.eq_zero_or_pos n)
   rintro rfl
-  rw [pow_zero] at h 
+  rw [pow_zero] at h
   have : (0 : K) = 1 := by apply fintype.card_le_one_iff.mp (le_of_eq h)
   exact absurd this zero_ne_one
 #align finite_field.card FiniteField.card
@@ -207,7 +207,7 @@ theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣
   constructor
   · intro h; apply h
   · intro h y
-    simp_rw [← mem_powers_iff_mem_zpowers] at hx 
+    simp_rw [← mem_powers_iff_mem_zpowers] at hx
     rcases hx y with ⟨j, rfl⟩
     rw [← pow_mul, mul_comm, pow_mul, h, one_pow]
 #align finite_field.forall_pow_eq_one_iff FiniteField.forall_pow_eq_one_iff
@@ -344,7 +344,7 @@ theorem expand_card (f : K[X]) : expand K q f = f ^ q :=
   letI := hp
   rcases FiniteField.card K p with ⟨⟨n, npos⟩, ⟨hp, hn⟩⟩
   haveI : Fact p.prime := ⟨hp⟩
-  dsimp at hn 
+  dsimp at hn
   rw [hn, ← map_expand_pow_char, frobenius_pow hn, RingHom.one_def, map_id]
 #align finite_field.expand_card FiniteField.expand_card
 -/
@@ -359,7 +359,7 @@ open FiniteField Polynomial
 theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p, a ^ 2 + b ^ 2 = x :=
   by
   cases' hp.1.eq_two_or_odd with hp2 hp_odd
-  · subst p; change Fin 2 at x ; fin_cases x; · use 0; simp; · use 0, 1; simp
+  · subst p; change Fin 2 at x; fin_cases x; · use 0; simp; · use 0, 1; simp
   let f : (ZMod p)[X] := X ^ 2
   let g : (ZMod p)[X] := X ^ 2 - C x
   obtain ⟨a, b, hab⟩ : ∃ a b, f.eval a + g.eval b = 0 :=
@@ -412,7 +412,7 @@ theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.Coprime x n) : x ^ φ n ≡ 1
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
   have := ZMod.pow_totient x'
-  apply_fun (coe : Units (ZMod n) → ZMod n) at this 
+  apply_fun (coe : Units (ZMod n) → ZMod n) at this
   simpa only [-ZMod.pow_totient, Nat.succ_eq_add_one, Nat.cast_pow, Units.val_one, Nat.cast_one,
     coe_unit_of_coprime, Units.val_pow_eq_pow_val]
 #align nat.modeq.pow_totient Nat.ModEq.pow_totient
@@ -443,7 +443,7 @@ namespace ZMod
 /-- A variation on Fermat's little theorem. See `zmod.pow_card_sub_one_eq_one` -/
 @[simp]
 theorem pow_card {p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p = x := by
-  have h := FiniteField.pow_card x; rwa [ZMod.card p] at h 
+  have h := FiniteField.pow_card x; rwa [ZMod.card p] at h
 #align zmod.pow_card ZMod.pow_card
 -/
 
@@ -481,7 +481,7 @@ theorem units_pow_card_sub_one_eq_one (p : ℕ) [Fact p.Prime] (a : (ZMod p)ˣ)
 #print ZMod.pow_card_sub_one_eq_one /-
 /-- **Fermat's Little Theorem**: for all nonzero `a : zmod p`, we have `a ^ (p - 1) = 1`. -/
 theorem pow_card_sub_one_eq_one {p : ℕ} [Fact p.Prime] {a : ZMod p} (ha : a ≠ 0) :
-    a ^ (p - 1) = 1 := by have h := pow_card_sub_one_eq_one a ha; rwa [ZMod.card p] at h 
+    a ^ (p - 1) = 1 := by have h := pow_card_sub_one_eq_one a ha; rwa [ZMod.card p] at h
 #align zmod.pow_card_sub_one_eq_one ZMod.pow_card_sub_one_eq_one
 -/
 
@@ -502,7 +502,7 @@ open Polynomial
 
 #print ZMod.expand_card /-
 theorem expand_card {p : ℕ} [Fact p.Prime] (f : Polynomial (ZMod p)) :
-    expand (ZMod p) p f = f ^ p := by have h := FiniteField.expand_card f; rwa [ZMod.card p] at h 
+    expand (ZMod p) p f = f ^ p := by have h := FiniteField.expand_card f; rwa [ZMod.card p] at h
 #align zmod.expand_card ZMod.expand_card
 -/
 
@@ -552,7 +552,7 @@ theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a :=
     simp only [injective, Classical.not_forall, exists_prop]
     refine' ⟨-1, 1, _, Ring.neg_one_ne_one_of_char_ne_two hF⟩
     simp only [sq, one_pow, neg_one_sq]
-  rw [Finite.injective_iff_surjective] at h 
+  rw [Finite.injective_iff_surjective] at h
   -- sq not surjective
   simp_rw [IsSquare, ← pow_two, @eq_comm _ _ (_ ^ 2)]
   push_neg at h ⊢
@@ -576,7 +576,7 @@ theorem even_card_iff_char_two : ringChar F = 2 ↔ Fintype.card F % 2 = 0 :=
     simp only [Nat.bit0_mod_two, zero_pow, Ne.def, PNat.ne_zero, not_false_iff, Nat.zero_mod]
   · rw [← Nat.even_iff, Nat.even_pow]
     rintro ⟨hev, hnz⟩
-    rw [Nat.even_iff, Nat.mod_mod] at hev 
+    rw [Nat.even_iff, Nat.mod_mod] at hev
     exact (Nat.Prime.eq_two_or_odd hp).resolve_right (ne_of_eq_of_ne hev zero_ne_one)
 #align finite_field.even_card_iff_char_two FiniteField.even_card_iff_char_two
 -/
@@ -600,7 +600,7 @@ theorem pow_dichotomy (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
   by
   have h₁ := FiniteField.pow_card_sub_one_eq_one a ha
   rw [← Nat.two_mul_odd_div_two (FiniteField.odd_card_of_char_ne_two hF), mul_comm, pow_mul,
-    pow_two] at h₁ 
+    pow_two] at h₁
   exact mul_self_eq_one_iff.mp h₁
 #align finite_field.pow_dichotomy FiniteField.pow_dichotomy
 -/
@@ -623,7 +623,7 @@ theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
   · subst a; intro h
     have key : 2 * (Fintype.card F / 2) ∣ n * (Fintype.card F / 2) :=
       by
-      rw [← pow_mul] at h 
+      rw [← pow_mul] at h
       rw [hodd, ← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hg]
       apply orderOf_dvd_of_pow_eq_one h
     have : 0 < Fintype.card F / 2 := Nat.div_pos Fintype.one_lt_card (by norm_num)
Diff
@@ -573,7 +573,7 @@ theorem even_card_iff_char_two : ringChar F = 2 ↔ Fintype.card F % 2 = 0 :=
   constructor
   · intro hF
     rw [hF]
-    simp only [Nat.bit0_mod_two, zero_pow', Ne.def, PNat.ne_zero, not_false_iff, Nat.zero_mod]
+    simp only [Nat.bit0_mod_two, zero_pow, Ne.def, PNat.ne_zero, not_false_iff, Nat.zero_mod]
   · rw [← Nat.even_iff, Nat.even_pow]
     rintro ⟨hev, hnz⟩
     rw [Nat.even_iff, Nat.mod_mod] at hev 
Diff
@@ -112,7 +112,13 @@ end Polynomial
 
 #print FiniteField.prod_univ_units_id_eq_neg_one /-
 theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
-    ∏ x : Kˣ, x = (-1 : Kˣ) := by classical
+    ∏ x : Kˣ, x = (-1 : Kˣ) := by
+  classical
+  have : ∏ x in (@univ Kˣ _).eraseₓ (-1), x = 1 :=
+    prod_involution (fun x _ => x⁻¹) (by simp)
+      (fun a => by simp (config := { contextual := true }) [Units.inv_eq_self_iff])
+      (fun a => by simp [@inv_eq_iff_eq_inv _ _ a]) (by simp)
+  rw [← insert_erase (mem_univ (-1 : Kˣ)), prod_insert (not_mem_erase _ _), this, mul_one]
 #align finite_field.prod_univ_units_id_eq_neg_one FiniteField.prod_univ_units_id_eq_neg_one
 -/
 
@@ -125,7 +131,10 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 :=
   calc
     a ^ (Fintype.card K - 1) = (Units.mk0 a ha ^ (Fintype.card K - 1) : Kˣ) := by
       rw [Units.val_pow_eq_pow_val, Units.val_mk0]
-    _ = 1 := by classical
+    _ = 1 := by
+      classical
+      rw [← Fintype.card_units, pow_card_eq_one]
+      rfl
 #align finite_field.pow_card_sub_one_eq_one FiniteField.pow_card_sub_one_eq_one
 -/
 
@@ -191,7 +200,16 @@ theorem cast_card_eq_zero : (q : K) = 0 :=
 -/
 
 #print FiniteField.forall_pow_eq_one_iff /-
-theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣ i := by classical
+theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣ i := by
+  classical
+  obtain ⟨x, hx⟩ := IsCyclic.exists_generator Kˣ
+  rw [← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hx, orderOf_dvd_iff_pow_eq_one]
+  constructor
+  · intro h; apply h
+  · intro h y
+    simp_rw [← mem_powers_iff_mem_zpowers] at hx 
+    rcases hx y with ⟨j, rfl⟩
+    rw [← pow_mul, mul_comm, pow_mul, h, one_pow]
 #align finite_field.forall_pow_eq_one_iff FiniteField.forall_pow_eq_one_iff
 -/
 
@@ -204,7 +222,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) : ∑ x : Kˣ, (x ^ i : K) = if q
     { toFun := fun x => x ^ i
       map_one' := by rw [Units.val_one, one_pow]
       map_mul' := by intros; rw [Units.val_mul, mul_pow] }
-  have : Decidable (φ = 1) := by classical
+  have : Decidable (φ = 1) := by classical infer_instance
   calc
     ∑ x : Kˣ, φ x = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
     _ = if q - 1 ∣ i then -1 else 0 := _
@@ -228,6 +246,18 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0
   by_cases hi : i = 0
   · simp only [hi, nsmul_one, sum_const, pow_zero, card_univ, cast_card_eq_zero]
   classical
+  have hiq : ¬q - 1 ∣ i := by contrapose! h; exact Nat.le_of_dvd (Nat.pos_of_ne_zero hi) h
+  let φ : Kˣ ↪ K := ⟨coe, Units.ext⟩
+  have : univ.map φ = univ \ {0} := by
+    ext x
+    simp only [true_and_iff, embedding.coe_fn_mk, mem_sdiff, Units.exists_iff_ne_zero, mem_univ,
+      mem_map, exists_prop_of_true, mem_singleton]
+  calc
+    ∑ x : K, x ^ i = ∑ x in univ \ {(0 : K)}, x ^ i := by
+      rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton, zero_pow (Nat.pos_of_ne_zero hi),
+        add_zero]
+    _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
+    _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 -/
 
@@ -275,7 +305,22 @@ end
 variable (p : ℕ) [Fact p.Prime] [Algebra (ZMod p) K]
 
 #print FiniteField.roots_X_pow_card_sub_X /-
-theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := by classical
+theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := by
+  classical
+  have aux : (X ^ q - X : K[X]) ≠ 0 := X_pow_card_sub_X_ne_zero K Fintype.one_lt_card
+  have : (roots (X ^ q - X : K[X])).toFinset = Finset.univ :=
+    by
+    rw [eq_univ_iff_forall]
+    intro x
+    rw [Multiset.mem_toFinset, mem_roots aux, is_root.def, eval_sub, eval_pow, eval_X, sub_eq_zero,
+      pow_card]
+  rw [← this, Multiset.toFinset_val, eq_comm, Multiset.dedup_eq_self]
+  apply nodup_roots
+  rw [separable_def]
+  convert is_coprime_one_right.neg_right using 1
+  ·
+    rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
+      MulZeroClass.zero_mul, zero_sub]
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_X_pow_card_sub_X
 -/
 
@@ -564,7 +609,27 @@ theorem pow_dichotomy (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
 /-- A unit `a` of a finite field `F` of odd characteristic is a square
 if and only if `a ^ (#F / 2) = 1`. -/
 theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
-    IsSquare a ↔ a ^ (Fintype.card F / 2) = 1 := by classical
+    IsSquare a ↔ a ^ (Fintype.card F / 2) = 1 := by
+  classical
+  obtain ⟨g, hg⟩ := IsCyclic.exists_generator Fˣ
+  obtain ⟨n, hn⟩ : a ∈ Submonoid.powers g := by rw [mem_powers_iff_mem_zpowers]; apply hg
+  have hodd := Nat.two_mul_odd_div_two (FiniteField.odd_card_of_char_ne_two hF)
+  constructor
+  · rintro ⟨y, rfl⟩
+    rw [← pow_two, ← pow_mul, hodd]
+    apply_fun @coe Fˣ F _ using Units.ext
+    · push_cast
+      exact FiniteField.pow_card_sub_one_eq_one (y : F) (Units.ne_zero y)
+  · subst a; intro h
+    have key : 2 * (Fintype.card F / 2) ∣ n * (Fintype.card F / 2) :=
+      by
+      rw [← pow_mul] at h 
+      rw [hodd, ← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hg]
+      apply orderOf_dvd_of_pow_eq_one h
+    have : 0 < Fintype.card F / 2 := Nat.div_pos Fintype.one_lt_card (by norm_num)
+    obtain ⟨m, rfl⟩ := Nat.dvd_of_mul_dvd_mul_right this key
+    refine' ⟨g ^ m, _⟩
+    rw [mul_comm, pow_mul, pow_two]
 #align finite_field.unit_is_square_iff FiniteField.unit_isSquare_iff
 -/
 
Diff
@@ -112,13 +112,7 @@ end Polynomial
 
 #print FiniteField.prod_univ_units_id_eq_neg_one /-
 theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
-    ∏ x : Kˣ, x = (-1 : Kˣ) := by
-  classical
-  have : ∏ x in (@univ Kˣ _).eraseₓ (-1), x = 1 :=
-    prod_involution (fun x _ => x⁻¹) (by simp)
-      (fun a => by simp (config := { contextual := true }) [Units.inv_eq_self_iff])
-      (fun a => by simp [@inv_eq_iff_eq_inv _ _ a]) (by simp)
-  rw [← insert_erase (mem_univ (-1 : Kˣ)), prod_insert (not_mem_erase _ _), this, mul_one]
+    ∏ x : Kˣ, x = (-1 : Kˣ) := by classical
 #align finite_field.prod_univ_units_id_eq_neg_one FiniteField.prod_univ_units_id_eq_neg_one
 -/
 
@@ -131,10 +125,7 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 :=
   calc
     a ^ (Fintype.card K - 1) = (Units.mk0 a ha ^ (Fintype.card K - 1) : Kˣ) := by
       rw [Units.val_pow_eq_pow_val, Units.val_mk0]
-    _ = 1 := by
-      classical
-      rw [← Fintype.card_units, pow_card_eq_one]
-      rfl
+    _ = 1 := by classical
 #align finite_field.pow_card_sub_one_eq_one FiniteField.pow_card_sub_one_eq_one
 -/
 
@@ -200,16 +191,7 @@ theorem cast_card_eq_zero : (q : K) = 0 :=
 -/
 
 #print FiniteField.forall_pow_eq_one_iff /-
-theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣ i := by
-  classical
-  obtain ⟨x, hx⟩ := IsCyclic.exists_generator Kˣ
-  rw [← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hx, orderOf_dvd_iff_pow_eq_one]
-  constructor
-  · intro h; apply h
-  · intro h y
-    simp_rw [← mem_powers_iff_mem_zpowers] at hx 
-    rcases hx y with ⟨j, rfl⟩
-    rw [← pow_mul, mul_comm, pow_mul, h, one_pow]
+theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣ i := by classical
 #align finite_field.forall_pow_eq_one_iff FiniteField.forall_pow_eq_one_iff
 -/
 
@@ -222,7 +204,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) : ∑ x : Kˣ, (x ^ i : K) = if q
     { toFun := fun x => x ^ i
       map_one' := by rw [Units.val_one, one_pow]
       map_mul' := by intros; rw [Units.val_mul, mul_pow] }
-  have : Decidable (φ = 1) := by classical infer_instance
+  have : Decidable (φ = 1) := by classical
   calc
     ∑ x : Kˣ, φ x = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
     _ = if q - 1 ∣ i then -1 else 0 := _
@@ -246,18 +228,6 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0
   by_cases hi : i = 0
   · simp only [hi, nsmul_one, sum_const, pow_zero, card_univ, cast_card_eq_zero]
   classical
-  have hiq : ¬q - 1 ∣ i := by contrapose! h; exact Nat.le_of_dvd (Nat.pos_of_ne_zero hi) h
-  let φ : Kˣ ↪ K := ⟨coe, Units.ext⟩
-  have : univ.map φ = univ \ {0} := by
-    ext x
-    simp only [true_and_iff, embedding.coe_fn_mk, mem_sdiff, Units.exists_iff_ne_zero, mem_univ,
-      mem_map, exists_prop_of_true, mem_singleton]
-  calc
-    ∑ x : K, x ^ i = ∑ x in univ \ {(0 : K)}, x ^ i := by
-      rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton, zero_pow (Nat.pos_of_ne_zero hi),
-        add_zero]
-    _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
-    _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 -/
 
@@ -305,22 +275,7 @@ end
 variable (p : ℕ) [Fact p.Prime] [Algebra (ZMod p) K]
 
 #print FiniteField.roots_X_pow_card_sub_X /-
-theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := by
-  classical
-  have aux : (X ^ q - X : K[X]) ≠ 0 := X_pow_card_sub_X_ne_zero K Fintype.one_lt_card
-  have : (roots (X ^ q - X : K[X])).toFinset = Finset.univ :=
-    by
-    rw [eq_univ_iff_forall]
-    intro x
-    rw [Multiset.mem_toFinset, mem_roots aux, is_root.def, eval_sub, eval_pow, eval_X, sub_eq_zero,
-      pow_card]
-  rw [← this, Multiset.toFinset_val, eq_comm, Multiset.dedup_eq_self]
-  apply nodup_roots
-  rw [separable_def]
-  convert is_coprime_one_right.neg_right using 1
-  ·
-    rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
-      MulZeroClass.zero_mul, zero_sub]
+theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := by classical
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_X_pow_card_sub_X
 -/
 
@@ -609,27 +564,7 @@ theorem pow_dichotomy (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
 /-- A unit `a` of a finite field `F` of odd characteristic is a square
 if and only if `a ^ (#F / 2) = 1`. -/
 theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
-    IsSquare a ↔ a ^ (Fintype.card F / 2) = 1 := by
-  classical
-  obtain ⟨g, hg⟩ := IsCyclic.exists_generator Fˣ
-  obtain ⟨n, hn⟩ : a ∈ Submonoid.powers g := by rw [mem_powers_iff_mem_zpowers]; apply hg
-  have hodd := Nat.two_mul_odd_div_two (FiniteField.odd_card_of_char_ne_two hF)
-  constructor
-  · rintro ⟨y, rfl⟩
-    rw [← pow_two, ← pow_mul, hodd]
-    apply_fun @coe Fˣ F _ using Units.ext
-    · push_cast
-      exact FiniteField.pow_card_sub_one_eq_one (y : F) (Units.ne_zero y)
-  · subst a; intro h
-    have key : 2 * (Fintype.card F / 2) ∣ n * (Fintype.card F / 2) :=
-      by
-      rw [← pow_mul] at h 
-      rw [hodd, ← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hg]
-      apply orderOf_dvd_of_pow_eq_one h
-    have : 0 < Fintype.card F / 2 := Nat.div_pos Fintype.one_lt_card (by norm_num)
-    obtain ⟨m, rfl⟩ := Nat.dvd_of_mul_dvd_mul_right this key
-    refine' ⟨g ^ m, _⟩
-    rw [mul_comm, pow_mul, pow_two]
+    IsSquare a ↔ a ^ (Fintype.card F / 2) = 1 := by classical
 #align finite_field.unit_is_square_iff FiniteField.unit_isSquare_iff
 -/
 
Diff
@@ -549,7 +549,7 @@ theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a :=
   let sq : F → F := fun x => x ^ 2
   have h : ¬injective sq :=
     by
-    simp only [injective, not_forall, exists_prop]
+    simp only [injective, Classical.not_forall, exists_prop]
     refine' ⟨-1, 1, _, Ring.neg_one_ne_one_of_char_ne_two hF⟩
     simp only [sq, one_pow, neg_one_sq]
   rw [Finite.injective_iff_surjective] at h 
Diff
@@ -3,9 +3,9 @@ Copyright (c) 2018 Chris Hughes. All rights reserved.
 Released under Apache 2.0 license as described in the file LICENSE.
 Authors: Chris Hughes, Joey van Langen, Casper Putz
 -/
-import Mathbin.FieldTheory.Separable
-import Mathbin.RingTheory.IntegralDomain
-import Mathbin.Tactic.ApplyFun
+import FieldTheory.Separable
+import RingTheory.IntegralDomain
+import Tactic.ApplyFun
 
 #align_import field_theory.finite.basic from "leanprover-community/mathlib"@"af471b9e3ce868f296626d33189b4ce730fa4c00"
 
Diff
@@ -407,7 +407,7 @@ theorem ZMod.pow_totient {n : ℕ} (x : (ZMod n)ˣ) : x ^ φ n = 1 :=
 #print Nat.ModEq.pow_totient /-
 /-- The **Fermat-Euler totient theorem**. `zmod.pow_totient` is an alternative statement
   of the same theorem. -/
-theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1 [MOD n] :=
+theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.Coprime x n) : x ^ φ n ≡ 1 [MOD n] :=
   by
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
Diff
@@ -2,16 +2,13 @@
 Copyright (c) 2018 Chris Hughes. All rights reserved.
 Released under Apache 2.0 license as described in the file LICENSE.
 Authors: Chris Hughes, Joey van Langen, Casper Putz
-
-! This file was ported from Lean 3 source module field_theory.finite.basic
-! leanprover-community/mathlib commit af471b9e3ce868f296626d33189b4ce730fa4c00
-! Please do not edit these lines, except to modify the commit id
-! if you have ported upstream changes.
 -/
 import Mathbin.FieldTheory.Separable
 import Mathbin.RingTheory.IntegralDomain
 import Mathbin.Tactic.ApplyFun
 
+#align_import field_theory.finite.basic from "leanprover-community/mathlib"@"af471b9e3ce868f296626d33189b4ce730fa4c00"
+
 /-!
 # Finite fields
 
Diff
@@ -51,7 +51,6 @@ diamonds, as `fintype` carries data.
 
 variable {K : Type _} {R : Type _}
 
--- mathport name: exprq
 local notation "q" => Fintype.card K
 
 open Finset Function
@@ -80,6 +79,7 @@ theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp :
 #align finite_field.card_image_polynomial_eval FiniteField.card_image_polynomial_eval
 -/
 
+#print FiniteField.exists_root_sum_quadratic /-
 /-- If `f` and `g` are quadratic polynomials, then the `f.eval a + g.eval b = 0` has a solution. -/
 theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2) (hg2 : degree g = 2)
     (hR : Fintype.card R % 2 = 1) : ∃ a b, f.eval a + g.eval b = 0 :=
@@ -109,9 +109,11 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
           simp [nat_degree_eq_of_degree_eq_some hf2, nat_degree_eq_of_degree_eq_some hg2, bit0,
             mul_add]
 #align finite_field.exists_root_sum_quadratic FiniteField.exists_root_sum_quadratic
+-/
 
 end Polynomial
 
+#print FiniteField.prod_univ_units_id_eq_neg_one /-
 theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
     ∏ x : Kˣ, x = (-1 : Kˣ) := by
   classical
@@ -121,11 +123,13 @@ theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
       (fun a => by simp [@inv_eq_iff_eq_inv _ _ a]) (by simp)
   rw [← insert_erase (mem_univ (-1 : Kˣ)), prod_insert (not_mem_erase _ _), this, mul_one]
 #align finite_field.prod_univ_units_id_eq_neg_one FiniteField.prod_univ_units_id_eq_neg_one
+-/
 
 section
 
 variable [GroupWithZero K] [Fintype K]
 
+#print FiniteField.pow_card_sub_one_eq_one /-
 theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 :=
   calc
     a ^ (Fintype.card K - 1) = (Units.mk0 a ha ^ (Fintype.card K - 1) : Kˣ) := by
@@ -135,6 +139,7 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 :=
       rw [← Fintype.card_units, pow_card_eq_one]
       rfl
 #align finite_field.pow_card_sub_one_eq_one FiniteField.pow_card_sub_one_eq_one
+-/
 
 #print FiniteField.pow_card /-
 theorem pow_card (a : K) : a ^ q = a :=
@@ -159,6 +164,7 @@ end
 
 variable (K) [Field K] [Fintype K]
 
+#print FiniteField.card /-
 theorem card (p : ℕ) [CharP K p] : ∃ n : ℕ+, Nat.Prime p ∧ q = p ^ (n : ℕ) :=
   by
   haveI hp : Fact p.prime := ⟨CharP.char_is_prime K p⟩
@@ -172,6 +178,7 @@ theorem card (p : ℕ) [CharP K p] : ∃ n : ℕ+, Nat.Prime p ∧ q = p ^ (n :
   have : (0 : K) = 1 := by apply fintype.card_le_one_iff.mp (le_of_eq h)
   exact absurd this zero_ne_one
 #align finite_field.card FiniteField.card
+-/
 
 #print FiniteField.card' /-
 -- this statement doesn't use `q` because we want `K` to be an explicit parameter
@@ -181,6 +188,7 @@ theorem card' : ∃ (p : ℕ) (n : ℕ+), Nat.Prime p ∧ Fintype.card K = p ^ (
 #align finite_field.card' FiniteField.card'
 -/
 
+#print FiniteField.cast_card_eq_zero /-
 @[simp]
 theorem cast_card_eq_zero : (q : K) = 0 :=
   by
@@ -192,7 +200,9 @@ theorem cast_card_eq_zero : (q : K) = 0 :=
     rw [← pow_one p]
   exact pow_dvd_pow _ n.2
 #align finite_field.cast_card_eq_zero FiniteField.cast_card_eq_zero
+-/
 
+#print FiniteField.forall_pow_eq_one_iff /-
 theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣ i := by
   classical
   obtain ⟨x, hx⟩ := IsCyclic.exists_generator Kˣ
@@ -204,7 +214,9 @@ theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣
     rcases hx y with ⟨j, rfl⟩
     rw [← pow_mul, mul_comm, pow_mul, h, one_pow]
 #align finite_field.forall_pow_eq_one_iff FiniteField.forall_pow_eq_one_iff
+-/
 
+#print FiniteField.sum_pow_units /-
 /-- The sum of `x ^ i` as `x` ranges over the units of a finite field of cardinality `q`
 is equal to `0` unless `(q - 1) ∣ i`, in which case the sum is `q - 1`. -/
 theorem sum_pow_units [Fintype Kˣ] (i : ℕ) : ∑ x : Kˣ, (x ^ i : K) = if q - 1 ∣ i then -1 else 0 :=
@@ -227,7 +239,9 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) : ∑ x : Kˣ, (x ^ i : K) = if q
   rw [Units.ext_iff, Units.val_pow_eq_pow_val, Units.val_one, MonoidHom.one_apply]
   rfl
 #align finite_field.sum_pow_units FiniteField.sum_pow_units
+-/
 
+#print FiniteField.sum_pow_lt_card_sub_one /-
 /-- The sum of `x ^ i` as `x` ranges over a finite field of cardinality `q`
 is equal to `0` if `i < q - 1`. -/
 theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0 :=
@@ -248,6 +262,7 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0
     _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
     _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
+-/
 
 open Polynomial
 
@@ -255,6 +270,7 @@ section
 
 variable (K' : Type _) [Field K'] {p n : ℕ}
 
+#print FiniteField.X_pow_card_sub_X_natDegree_eq /-
 theorem X_pow_card_sub_X_natDegree_eq (hp : 1 < p) : (X ^ p - X : K'[X]).natDegree = p :=
   by
   have h1 : (X : K'[X]).degree < (X ^ p : K'[X]).degree :=
@@ -263,27 +279,35 @@ theorem X_pow_card_sub_X_natDegree_eq (hp : 1 < p) : (X ^ p - X : K'[X]).natDegr
     exact_mod_cast hp
   rw [nat_degree_eq_of_degree_eq (degree_sub_eq_left_of_degree_lt h1), nat_degree_X_pow]
 #align finite_field.X_pow_card_sub_X_nat_degree_eq FiniteField.X_pow_card_sub_X_natDegree_eq
+-/
 
+#print FiniteField.X_pow_card_pow_sub_X_natDegree_eq /-
 theorem X_pow_card_pow_sub_X_natDegree_eq (hn : n ≠ 0) (hp : 1 < p) :
     (X ^ p ^ n - X : K'[X]).natDegree = p ^ n :=
   X_pow_card_sub_X_natDegree_eq K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
 #align finite_field.X_pow_card_pow_sub_X_nat_degree_eq FiniteField.X_pow_card_pow_sub_X_natDegree_eq
+-/
 
+#print FiniteField.X_pow_card_sub_X_ne_zero /-
 theorem X_pow_card_sub_X_ne_zero (hp : 1 < p) : (X ^ p - X : K'[X]) ≠ 0 :=
   ne_zero_of_natDegree_gt <|
     calc
       1 < _ := hp
       _ = _ := (X_pow_card_sub_X_natDegree_eq K' hp).symm
 #align finite_field.X_pow_card_sub_X_ne_zero FiniteField.X_pow_card_sub_X_ne_zero
+-/
 
+#print FiniteField.X_pow_card_pow_sub_X_ne_zero /-
 theorem X_pow_card_pow_sub_X_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (X ^ p ^ n - X : K'[X]) ≠ 0 :=
   X_pow_card_sub_X_ne_zero K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
 #align finite_field.X_pow_card_pow_sub_X_ne_zero FiniteField.X_pow_card_pow_sub_X_ne_zero
+-/
 
 end
 
 variable (p : ℕ) [Fact p.Prime] [Algebra (ZMod p) K]
 
+#print FiniteField.roots_X_pow_card_sub_X /-
 theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := by
   classical
   have aux : (X ^ q - X : K[X]) ≠ 0 := X_pow_card_sub_X_ne_zero K Fintype.one_lt_card
@@ -301,18 +325,22 @@ theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := b
     rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
       MulZeroClass.zero_mul, zero_sub]
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_X_pow_card_sub_X
+-/
 
 variable {K}
 
+#print FiniteField.frobenius_pow /-
 theorem frobenius_pow {p : ℕ} [Fact p.Prime] [CharP K p] {n : ℕ} (hcard : q = p ^ n) :
     frobenius K p ^ n = 1 := by
   ext; conv_rhs => rw [RingHom.one_def, RingHom.id_apply, ← pow_card x, hcard]; clear hcard
   induction n; · simp
   rw [pow_succ, pow_succ', pow_mul, RingHom.mul_def, RingHom.comp_apply, frobenius_def, n_ih]
 #align finite_field.frobenius_pow FiniteField.frobenius_pow
+-/
 
 open Polynomial
 
+#print FiniteField.expand_card /-
 theorem expand_card (f : K[X]) : expand K q f = f ^ q :=
   by
   cases' CharP.exists K with p hp
@@ -322,6 +350,7 @@ theorem expand_card (f : K[X]) : expand K q f = f ^ q :=
   dsimp at hn 
   rw [hn, ← map_expand_pow_char, frobenius_pow hn, RingHom.one_def, map_id]
 #align finite_field.expand_card FiniteField.expand_card
+-/
 
 end FiniteField
 
@@ -329,6 +358,7 @@ namespace ZMod
 
 open FiniteField Polynomial
 
+#print ZMod.sq_add_sq /-
 theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p, a ^ 2 + b ^ 2 = x :=
   by
   cases' hp.1.eq_two_or_odd with hp2 hp_odd
@@ -342,11 +372,13 @@ theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p,
   rw [← sub_eq_zero]
   simpa only [eval_C, eval_X, eval_pow, eval_sub, ← add_sub_assoc] using hab
 #align zmod.sq_add_sq ZMod.sq_add_sq
+-/
 
 end ZMod
 
 namespace CharP
 
+#print CharP.sq_add_sq /-
 theorem sq_add_sq (R : Type _) [CommRing R] [IsDomain R] (p : ℕ) [NeZero p] [CharP R p] (x : ℤ) :
     ∃ a b : ℕ, (a ^ 2 + b ^ 2 : R) = x :=
   by
@@ -355,6 +387,7 @@ theorem sq_add_sq (R : Type _) [CommRing R] [IsDomain R] (p : ℕ) [NeZero p] [C
   refine' ⟨a.val, b.val, _⟩
   simpa using congr_arg (ZMod.castHom dvd_rfl R) hab
 #align char_p.sq_add_sq CharP.sq_add_sq
+-/
 
 end CharP
 
@@ -362,6 +395,7 @@ open scoped Nat
 
 open ZMod
 
+#print ZMod.pow_totient /-
 /-- The **Fermat-Euler totient theorem**. `nat.modeq.pow_totient` is an alternative statement
   of the same theorem. -/
 @[simp]
@@ -371,6 +405,7 @@ theorem ZMod.pow_totient {n : ℕ} (x : (ZMod n)ˣ) : x ^ φ n = 1 :=
   · rw [Nat.totient_zero, pow_zero]
   · rw [← card_units_eq_totient, pow_card_eq_one]
 #align zmod.pow_totient ZMod.pow_totient
+-/
 
 #print Nat.ModEq.pow_totient /-
 /-- The **Fermat-Euler totient theorem**. `zmod.pow_totient` is an alternative statement
@@ -407,12 +442,15 @@ open FiniteField
 
 namespace ZMod
 
+#print ZMod.pow_card /-
 /-- A variation on Fermat's little theorem. See `zmod.pow_card_sub_one_eq_one` -/
 @[simp]
 theorem pow_card {p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p = x := by
   have h := FiniteField.pow_card x; rwa [ZMod.card p] at h 
 #align zmod.pow_card ZMod.pow_card
+-/
 
+#print ZMod.pow_card_pow /-
 @[simp]
 theorem pow_card_pow {n p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p ^ n = x :=
   by
@@ -420,44 +458,60 @@ theorem pow_card_pow {n p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p ^ n = x :=
   · simp
   · simp [pow_succ, pow_mul, ih, pow_card]
 #align zmod.pow_card_pow ZMod.pow_card_pow
+-/
 
+#print ZMod.frobenius_zmod /-
 @[simp]
 theorem frobenius_zmod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom.id _ := by ext a;
   rw [frobenius_def, ZMod.pow_card, RingHom.id_apply]
 #align zmod.frobenius_zmod ZMod.frobenius_zmod
+-/
 
+#print ZMod.card_units /-
 @[simp]
 theorem card_units (p : ℕ) [Fact p.Prime] : Fintype.card (ZMod p)ˣ = p - 1 := by
   rw [Fintype.card_units, card]
 #align zmod.card_units ZMod.card_units
+-/
 
+#print ZMod.units_pow_card_sub_one_eq_one /-
 /-- **Fermat's Little Theorem**: for every unit `a` of `zmod p`, we have `a ^ (p - 1) = 1`. -/
 theorem units_pow_card_sub_one_eq_one (p : ℕ) [Fact p.Prime] (a : (ZMod p)ˣ) : a ^ (p - 1) = 1 := by
   rw [← card_units p, pow_card_eq_one]
 #align zmod.units_pow_card_sub_one_eq_one ZMod.units_pow_card_sub_one_eq_one
+-/
 
+#print ZMod.pow_card_sub_one_eq_one /-
 /-- **Fermat's Little Theorem**: for all nonzero `a : zmod p`, we have `a ^ (p - 1) = 1`. -/
 theorem pow_card_sub_one_eq_one {p : ℕ} [Fact p.Prime] {a : ZMod p} (ha : a ≠ 0) :
     a ^ (p - 1) = 1 := by have h := pow_card_sub_one_eq_one a ha; rwa [ZMod.card p] at h 
 #align zmod.pow_card_sub_one_eq_one ZMod.pow_card_sub_one_eq_one
+-/
 
+#print ZMod.orderOf_units_dvd_card_sub_one /-
 theorem orderOf_units_dvd_card_sub_one {p : ℕ} [Fact p.Prime] (u : (ZMod p)ˣ) : orderOf u ∣ p - 1 :=
   orderOf_dvd_of_pow_eq_one <| units_pow_card_sub_one_eq_one _ _
 #align zmod.order_of_units_dvd_card_sub_one ZMod.orderOf_units_dvd_card_sub_one
+-/
 
+#print ZMod.orderOf_dvd_card_sub_one /-
 theorem orderOf_dvd_card_sub_one {p : ℕ} [Fact p.Prime] {a : ZMod p} (ha : a ≠ 0) :
     orderOf a ∣ p - 1 :=
   orderOf_dvd_of_pow_eq_one <| pow_card_sub_one_eq_one ha
 #align zmod.order_of_dvd_card_sub_one ZMod.orderOf_dvd_card_sub_one
+-/
 
 open Polynomial
 
+#print ZMod.expand_card /-
 theorem expand_card {p : ℕ} [Fact p.Prime] (f : Polynomial (ZMod p)) :
     expand (ZMod p) p f = f ^ p := by have h := FiniteField.expand_card f; rwa [ZMod.card p] at h 
 #align zmod.expand_card ZMod.expand_card
+-/
 
 end ZMod
 
+#print Int.ModEq.pow_card_sub_one_eq_one /-
 /-- **Fermat's Little Theorem**: for all `a : ℤ` coprime to `p`, we have
 `a ^ (p - 1) ≡ 1 [ZMOD p]`. -/
 theorem Int.ModEq.pow_card_sub_one_eq_one {p : ℕ} (hp : Nat.Prime p) {n : ℤ} (hpn : IsCoprime n p) :
@@ -470,6 +524,7 @@ theorem Int.ModEq.pow_card_sub_one_eq_one {p : ℕ} (hp : Nat.Prime p) {n : ℤ}
     exact ZMod.charP p
   simpa [← ZMod.int_cast_eq_int_cast_iff] using ZMod.pow_card_sub_one_eq_one this
 #align int.modeq.pow_card_sub_one_eq_one Int.ModEq.pow_card_sub_one_eq_one
+-/
 
 section
 
@@ -481,12 +536,15 @@ section Finite
 
 variable [Finite F]
 
+#print FiniteField.isSquare_of_char_two /-
 /-- In a finite field of characteristic `2`, all elements are squares. -/
 theorem isSquare_of_char_two (hF : ringChar F = 2) (a : F) : IsSquare a :=
   haveI hF' : CharP F 2 := ringChar.of_eq hF
   isSquare_of_charTwo' a
 #align finite_field.is_square_of_char_two FiniteField.isSquare_of_char_two
+-/
 
+#print FiniteField.exists_nonsquare /-
 /-- In a finite field of odd characteristic, not every element is a square. -/
 theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a :=
   by
@@ -503,6 +561,7 @@ theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a :=
   push_neg at h ⊢
   exact h
 #align finite_field.exists_nonsquare FiniteField.exists_nonsquare
+-/
 
 end Finite
 
@@ -537,6 +596,7 @@ theorem odd_card_of_char_ne_two (hF : ringChar F ≠ 2) : Fintype.card F % 2 = 1
 #align finite_field.odd_card_of_char_ne_two FiniteField.odd_card_of_char_ne_two
 -/
 
+#print FiniteField.pow_dichotomy /-
 /-- If `F` has odd characteristic, then for nonzero `a : F`, we have that `a ^ (#F / 2) = ±1`. -/
 theorem pow_dichotomy (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
     a ^ (Fintype.card F / 2) = 1 ∨ a ^ (Fintype.card F / 2) = -1 :=
@@ -546,7 +606,9 @@ theorem pow_dichotomy (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
     pow_two] at h₁ 
   exact mul_self_eq_one_iff.mp h₁
 #align finite_field.pow_dichotomy FiniteField.pow_dichotomy
+-/
 
+#print FiniteField.unit_isSquare_iff /-
 /-- A unit `a` of a finite field `F` of odd characteristic is a square
 if and only if `a ^ (#F / 2) = 1`. -/
 theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
@@ -572,7 +634,9 @@ theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
     refine' ⟨g ^ m, _⟩
     rw [mul_comm, pow_mul, pow_two]
 #align finite_field.unit_is_square_iff FiniteField.unit_isSquare_iff
+-/
 
+#print FiniteField.isSquare_iff /-
 /-- A non-zero `a : F` is a square if and only if `a ^ (#F / 2) = 1`. -/
 theorem isSquare_iff (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
     IsSquare a ↔ a ^ (Fintype.card F / 2) = 1 :=
@@ -586,6 +650,7 @@ theorem isSquare_iff (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
     have hy : y ≠ 0 := by rintro rfl; simpa [zero_pow] using ha
     refine' ⟨Units.mk0 y hy, _⟩; simp
 #align finite_field.is_square_iff FiniteField.isSquare_iff
+-/
 
 end FiniteField
 
Diff
@@ -113,9 +113,9 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
 end Polynomial
 
 theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
-    (∏ x : Kˣ, x) = (-1 : Kˣ) := by
+    ∏ x : Kˣ, x = (-1 : Kˣ) := by
   classical
-  have : (∏ x in (@univ Kˣ _).eraseₓ (-1), x) = 1 :=
+  have : ∏ x in (@univ Kˣ _).eraseₓ (-1), x = 1 :=
     prod_involution (fun x _ => x⁻¹) (by simp)
       (fun a => by simp (config := { contextual := true }) [Units.inv_eq_self_iff])
       (fun a => by simp [@inv_eq_iff_eq_inv _ _ a]) (by simp)
@@ -207,8 +207,7 @@ theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣
 
 /-- The sum of `x ^ i` as `x` ranges over the units of a finite field of cardinality `q`
 is equal to `0` unless `(q - 1) ∣ i`, in which case the sum is `q - 1`. -/
-theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
-    (∑ x : Kˣ, (x ^ i : K)) = if q - 1 ∣ i then -1 else 0 :=
+theorem sum_pow_units [Fintype Kˣ] (i : ℕ) : ∑ x : Kˣ, (x ^ i : K) = if q - 1 ∣ i then -1 else 0 :=
   by
   let φ : Kˣ →* K :=
     { toFun := fun x => x ^ i
@@ -216,7 +215,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
       map_mul' := by intros; rw [Units.val_mul, mul_pow] }
   have : Decidable (φ = 1) := by classical infer_instance
   calc
-    (∑ x : Kˣ, φ x) = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
+    ∑ x : Kˣ, φ x = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
     _ = if q - 1 ∣ i then -1 else 0 := _
   suffices q - 1 ∣ i ↔ φ = 1 by
     simp only [this]
@@ -231,7 +230,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
 
 /-- The sum of `x ^ i` as `x` ranges over a finite field of cardinality `q`
 is equal to `0` if `i < q - 1`. -/
-theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) = 0 :=
+theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0 :=
   by
   by_cases hi : i = 0
   · simp only [hi, nsmul_one, sum_const, pow_zero, card_univ, cast_card_eq_zero]
@@ -243,7 +242,7 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
     simp only [true_and_iff, embedding.coe_fn_mk, mem_sdiff, Units.exists_iff_ne_zero, mem_univ,
       mem_map, exists_prop_of_true, mem_singleton]
   calc
-    (∑ x : K, x ^ i) = ∑ x in univ \ {(0 : K)}, x ^ i := by
+    ∑ x : K, x ^ i = ∑ x in univ \ {(0 : K)}, x ^ i := by
       rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton, zero_pow (Nat.pos_of_ne_zero hi),
         add_zero]
     _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
Diff
@@ -77,7 +77,6 @@ theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp :
         congr_arg card (by simp [Finset.ext_iff, mem_roots_sub_C hp])
       _ ≤ (p - C a).roots.card := (Multiset.toFinset_card_le _)
       _ ≤ _ := card_roots_sub_C' hp
-      
 #align finite_field.card_image_polynomial_eval FiniteField.card_image_polynomial_eval
 -/
 
@@ -109,7 +108,6 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
         rw [card_disjoint_union hd] <;>
           simp [nat_degree_eq_of_degree_eq_some hf2, nat_degree_eq_of_degree_eq_some hg2, bit0,
             mul_add]
-      
 #align finite_field.exists_root_sum_quadratic FiniteField.exists_root_sum_quadratic
 
 end Polynomial
@@ -136,7 +134,6 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 :=
       classical
       rw [← Fintype.card_units, pow_card_eq_one]
       rfl
-    
 #align finite_field.pow_card_sub_one_eq_one FiniteField.pow_card_sub_one_eq_one
 
 #print FiniteField.pow_card /-
@@ -221,7 +218,6 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
   calc
     (∑ x : Kˣ, φ x) = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
     _ = if q - 1 ∣ i then -1 else 0 := _
-    
   suffices q - 1 ∣ i ↔ φ = 1 by
     simp only [this]
     split_ifs with h h; swap; rfl
@@ -252,7 +248,6 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
         add_zero]
     _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
     _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
-    
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 
 open Polynomial
@@ -280,7 +275,6 @@ theorem X_pow_card_sub_X_ne_zero (hp : 1 < p) : (X ^ p - X : K'[X]) ≠ 0 :=
     calc
       1 < _ := hp
       _ = _ := (X_pow_card_sub_X_natDegree_eq K' hp).symm
-      
 #align finite_field.X_pow_card_sub_X_ne_zero FiniteField.X_pow_card_sub_X_ne_zero
 
 theorem X_pow_card_pow_sub_X_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (X ^ p ^ n - X : K'[X]) ≠ 0 :=
Diff
@@ -429,9 +429,9 @@ theorem pow_card_pow {n p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p ^ n = x :=
 #align zmod.pow_card_pow ZMod.pow_card_pow
 
 @[simp]
-theorem frobenius_zMod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom.id _ := by ext a;
+theorem frobenius_zmod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom.id _ := by ext a;
   rw [frobenius_def, ZMod.pow_card, RingHom.id_apply]
-#align zmod.frobenius_zmod ZMod.frobenius_zMod
+#align zmod.frobenius_zmod ZMod.frobenius_zmod
 
 @[simp]
 theorem card_units (p : ℕ) [Fact p.Prime] : Fintype.card (ZMod p)ˣ = p - 1 := by
Diff
@@ -4,7 +4,7 @@ Released under Apache 2.0 license as described in the file LICENSE.
 Authors: Chris Hughes, Joey van Langen, Casper Putz
 
 ! This file was ported from Lean 3 source module field_theory.finite.basic
-! leanprover-community/mathlib commit 12a85fac627bea918960da036049d611b1a3ee43
+! leanprover-community/mathlib commit af471b9e3ce868f296626d33189b4ce730fa4c00
 ! Please do not edit these lines, except to modify the commit id
 ! if you have ported upstream changes.
 -/
@@ -15,6 +15,9 @@ import Mathbin.Tactic.ApplyFun
 /-!
 # Finite fields
 
+> THIS FILE IS SYNCHRONIZED WITH MATHLIB4.
+> Any changes to this file require a corresponding PR to mathlib4.
+
 This file contains basic results about finite fields.
 Throughout most of this file, `K` denotes a finite field
 and `q` is notation for the cardinality of `K`.
@@ -63,6 +66,7 @@ variable [CommRing R] [IsDomain R]
 
 open Polynomial
 
+#print FiniteField.card_image_polynomial_eval /-
 /-- The cardinality of a field is at most `n` times the cardinality of the image of a degree `n`
   polynomial -/
 theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp : 0 < p.degree) :
@@ -75,6 +79,7 @@ theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp :
       _ ≤ _ := card_roots_sub_C' hp
       
 #align finite_field.card_image_polynomial_eval FiniteField.card_image_polynomial_eval
+-/
 
 /-- If `f` and `g` are quadratic polynomials, then the `f.eval a + g.eval b = 0` has a solution. -/
 theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2) (hg2 : degree g = 2)
@@ -83,7 +88,7 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
   suffices ¬Disjoint (univ.image fun x : R => eval x f) (univ.image fun x : R => eval x (-g))
     by
     simp only [disjoint_left, mem_image] at this 
-    push_neg  at this 
+    push_neg at this 
     rcases this with ⟨x, ⟨a, _, ha⟩, ⟨b, _, hb⟩⟩
     exact ⟨a, b, by rw [ha, ← hb, eval_neg, neg_add_self]⟩
   fun hd : Disjoint _ _ =>
@@ -112,11 +117,11 @@ end Polynomial
 theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
     (∏ x : Kˣ, x) = (-1 : Kˣ) := by
   classical
-    have : (∏ x in (@univ Kˣ _).eraseₓ (-1), x) = 1 :=
-      prod_involution (fun x _ => x⁻¹) (by simp)
-        (fun a => by simp (config := { contextual := true }) [Units.inv_eq_self_iff])
-        (fun a => by simp [@inv_eq_iff_eq_inv _ _ a]) (by simp)
-    rw [← insert_erase (mem_univ (-1 : Kˣ)), prod_insert (not_mem_erase _ _), this, mul_one]
+  have : (∏ x in (@univ Kˣ _).eraseₓ (-1), x) = 1 :=
+    prod_involution (fun x _ => x⁻¹) (by simp)
+      (fun a => by simp (config := { contextual := true }) [Units.inv_eq_self_iff])
+      (fun a => by simp [@inv_eq_iff_eq_inv _ _ a]) (by simp)
+  rw [← insert_erase (mem_univ (-1 : Kˣ)), prod_insert (not_mem_erase _ _), this, mul_one]
 #align finite_field.prod_univ_units_id_eq_neg_one FiniteField.prod_univ_units_id_eq_neg_one
 
 section
@@ -129,11 +134,12 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 :=
       rw [Units.val_pow_eq_pow_val, Units.val_mk0]
     _ = 1 := by
       classical
-        rw [← Fintype.card_units, pow_card_eq_one]
-        rfl
+      rw [← Fintype.card_units, pow_card_eq_one]
+      rfl
     
 #align finite_field.pow_card_sub_one_eq_one FiniteField.pow_card_sub_one_eq_one
 
+#print FiniteField.pow_card /-
 theorem pow_card (a : K) : a ^ q = a :=
   by
   have hp : 0 < Fintype.card K := lt_trans zero_lt_one Fintype.one_lt_card
@@ -141,13 +147,16 @@ theorem pow_card (a : K) : a ^ q = a :=
   rw [← Nat.succ_pred_eq_of_pos hp, pow_succ, Nat.pred_eq_sub_one, pow_card_sub_one_eq_one a h,
     mul_one]
 #align finite_field.pow_card FiniteField.pow_card
+-/
 
+#print FiniteField.pow_card_pow /-
 theorem pow_card_pow (n : ℕ) (a : K) : a ^ q ^ n = a :=
   by
   induction' n with n ih
   · simp
   · simp [pow_succ, pow_mul, ih, pow_card]
 #align finite_field.pow_card_pow FiniteField.pow_card_pow
+-/
 
 end
 
@@ -167,11 +176,13 @@ theorem card (p : ℕ) [CharP K p] : ∃ n : ℕ+, Nat.Prime p ∧ q = p ^ (n :
   exact absurd this zero_ne_one
 #align finite_field.card FiniteField.card
 
+#print FiniteField.card' /-
 -- this statement doesn't use `q` because we want `K` to be an explicit parameter
 theorem card' : ∃ (p : ℕ) (n : ℕ+), Nat.Prime p ∧ Fintype.card K = p ^ (n : ℕ) :=
   let ⟨p, hc⟩ := CharP.exists K
   ⟨p, @FiniteField.card K _ _ p hc⟩
 #align finite_field.card' FiniteField.card'
+-/
 
 @[simp]
 theorem cast_card_eq_zero : (q : K) = 0 :=
@@ -187,15 +198,14 @@ theorem cast_card_eq_zero : (q : K) = 0 :=
 
 theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣ i := by
   classical
-    obtain ⟨x, hx⟩ := IsCyclic.exists_generator Kˣ
-    rw [← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hx,
-      orderOf_dvd_iff_pow_eq_one]
-    constructor
-    · intro h; apply h
-    · intro h y
-      simp_rw [← mem_powers_iff_mem_zpowers] at hx 
-      rcases hx y with ⟨j, rfl⟩
-      rw [← pow_mul, mul_comm, pow_mul, h, one_pow]
+  obtain ⟨x, hx⟩ := IsCyclic.exists_generator Kˣ
+  rw [← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hx, orderOf_dvd_iff_pow_eq_one]
+  constructor
+  · intro h; apply h
+  · intro h y
+    simp_rw [← mem_powers_iff_mem_zpowers] at hx 
+    rcases hx y with ⟨j, rfl⟩
+    rw [← pow_mul, mul_comm, pow_mul, h, one_pow]
 #align finite_field.forall_pow_eq_one_iff FiniteField.forall_pow_eq_one_iff
 
 /-- The sum of `x ^ i` as `x` ranges over the units of a finite field of cardinality `q`
@@ -230,19 +240,19 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
   by_cases hi : i = 0
   · simp only [hi, nsmul_one, sum_const, pow_zero, card_univ, cast_card_eq_zero]
   classical
-    have hiq : ¬q - 1 ∣ i := by contrapose! h; exact Nat.le_of_dvd (Nat.pos_of_ne_zero hi) h
-    let φ : Kˣ ↪ K := ⟨coe, Units.ext⟩
-    have : univ.map φ = univ \ {0} := by
-      ext x
-      simp only [true_and_iff, embedding.coe_fn_mk, mem_sdiff, Units.exists_iff_ne_zero, mem_univ,
-        mem_map, exists_prop_of_true, mem_singleton]
-    calc
-      (∑ x : K, x ^ i) = ∑ x in univ \ {(0 : K)}, x ^ i := by
-        rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton,
-          zero_pow (Nat.pos_of_ne_zero hi), add_zero]
-      _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
-      _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
-      
+  have hiq : ¬q - 1 ∣ i := by contrapose! h; exact Nat.le_of_dvd (Nat.pos_of_ne_zero hi) h
+  let φ : Kˣ ↪ K := ⟨coe, Units.ext⟩
+  have : univ.map φ = univ \ {0} := by
+    ext x
+    simp only [true_and_iff, embedding.coe_fn_mk, mem_sdiff, Units.exists_iff_ne_zero, mem_univ,
+      mem_map, exists_prop_of_true, mem_singleton]
+  calc
+    (∑ x : K, x ^ i) = ∑ x in univ \ {(0 : K)}, x ^ i := by
+      rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton, zero_pow (Nat.pos_of_ne_zero hi),
+        add_zero]
+    _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
+    _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
+    
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 
 open Polynomial
@@ -251,53 +261,53 @@ section
 
 variable (K' : Type _) [Field K'] {p n : ℕ}
 
-theorem x_pow_card_sub_x_natDegree_eq (hp : 1 < p) : (X ^ p - X : K'[X]).natDegree = p :=
+theorem X_pow_card_sub_X_natDegree_eq (hp : 1 < p) : (X ^ p - X : K'[X]).natDegree = p :=
   by
   have h1 : (X : K'[X]).degree < (X ^ p : K'[X]).degree :=
     by
     rw [degree_X_pow, degree_X]
     exact_mod_cast hp
   rw [nat_degree_eq_of_degree_eq (degree_sub_eq_left_of_degree_lt h1), nat_degree_X_pow]
-#align finite_field.X_pow_card_sub_X_nat_degree_eq FiniteField.x_pow_card_sub_x_natDegree_eq
+#align finite_field.X_pow_card_sub_X_nat_degree_eq FiniteField.X_pow_card_sub_X_natDegree_eq
 
-theorem x_pow_card_pow_sub_x_natDegree_eq (hn : n ≠ 0) (hp : 1 < p) :
+theorem X_pow_card_pow_sub_X_natDegree_eq (hn : n ≠ 0) (hp : 1 < p) :
     (X ^ p ^ n - X : K'[X]).natDegree = p ^ n :=
-  x_pow_card_sub_x_natDegree_eq K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
-#align finite_field.X_pow_card_pow_sub_X_nat_degree_eq FiniteField.x_pow_card_pow_sub_x_natDegree_eq
+  X_pow_card_sub_X_natDegree_eq K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
+#align finite_field.X_pow_card_pow_sub_X_nat_degree_eq FiniteField.X_pow_card_pow_sub_X_natDegree_eq
 
-theorem x_pow_card_sub_x_ne_zero (hp : 1 < p) : (X ^ p - X : K'[X]) ≠ 0 :=
+theorem X_pow_card_sub_X_ne_zero (hp : 1 < p) : (X ^ p - X : K'[X]) ≠ 0 :=
   ne_zero_of_natDegree_gt <|
     calc
       1 < _ := hp
-      _ = _ := (x_pow_card_sub_x_natDegree_eq K' hp).symm
+      _ = _ := (X_pow_card_sub_X_natDegree_eq K' hp).symm
       
-#align finite_field.X_pow_card_sub_X_ne_zero FiniteField.x_pow_card_sub_x_ne_zero
+#align finite_field.X_pow_card_sub_X_ne_zero FiniteField.X_pow_card_sub_X_ne_zero
 
-theorem x_pow_card_pow_sub_x_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (X ^ p ^ n - X : K'[X]) ≠ 0 :=
-  x_pow_card_sub_x_ne_zero K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
-#align finite_field.X_pow_card_pow_sub_X_ne_zero FiniteField.x_pow_card_pow_sub_x_ne_zero
+theorem X_pow_card_pow_sub_X_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (X ^ p ^ n - X : K'[X]) ≠ 0 :=
+  X_pow_card_sub_X_ne_zero K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
+#align finite_field.X_pow_card_pow_sub_X_ne_zero FiniteField.X_pow_card_pow_sub_X_ne_zero
 
 end
 
 variable (p : ℕ) [Fact p.Prime] [Algebra (ZMod p) K]
 
-theorem roots_x_pow_card_sub_x : roots (X ^ q - X : K[X]) = Finset.univ.val := by
+theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := by
   classical
-    have aux : (X ^ q - X : K[X]) ≠ 0 := X_pow_card_sub_X_ne_zero K Fintype.one_lt_card
-    have : (roots (X ^ q - X : K[X])).toFinset = Finset.univ :=
-      by
-      rw [eq_univ_iff_forall]
-      intro x
-      rw [Multiset.mem_toFinset, mem_roots aux, is_root.def, eval_sub, eval_pow, eval_X,
-        sub_eq_zero, pow_card]
-    rw [← this, Multiset.toFinset_val, eq_comm, Multiset.dedup_eq_self]
-    apply nodup_roots
-    rw [separable_def]
-    convert is_coprime_one_right.neg_right using 1
-    ·
-      rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
-        MulZeroClass.zero_mul, zero_sub]
-#align finite_field.roots_X_pow_card_sub_X FiniteField.roots_x_pow_card_sub_x
+  have aux : (X ^ q - X : K[X]) ≠ 0 := X_pow_card_sub_X_ne_zero K Fintype.one_lt_card
+  have : (roots (X ^ q - X : K[X])).toFinset = Finset.univ :=
+    by
+    rw [eq_univ_iff_forall]
+    intro x
+    rw [Multiset.mem_toFinset, mem_roots aux, is_root.def, eval_sub, eval_pow, eval_X, sub_eq_zero,
+      pow_card]
+  rw [← this, Multiset.toFinset_val, eq_comm, Multiset.dedup_eq_self]
+  apply nodup_roots
+  rw [separable_def]
+  convert is_coprime_one_right.neg_right using 1
+  ·
+    rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
+      MulZeroClass.zero_mul, zero_sub]
+#align finite_field.roots_X_pow_card_sub_X FiniteField.roots_X_pow_card_sub_X
 
 variable {K}
 
@@ -369,6 +379,7 @@ theorem ZMod.pow_totient {n : ℕ} (x : (ZMod n)ˣ) : x ^ φ n = 1 :=
   · rw [← card_units_eq_totient, pow_card_eq_one]
 #align zmod.pow_totient ZMod.pow_totient
 
+#print Nat.ModEq.pow_totient /-
 /-- The **Fermat-Euler totient theorem**. `zmod.pow_totient` is an alternative statement
   of the same theorem. -/
 theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1 [MOD n] :=
@@ -376,15 +387,17 @@ theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
   have := ZMod.pow_totient x'
-  apply_fun (coe : Units (ZMod n) → ZMod n)  at this 
+  apply_fun (coe : Units (ZMod n) → ZMod n) at this 
   simpa only [-ZMod.pow_totient, Nat.succ_eq_add_one, Nat.cast_pow, Units.val_one, Nat.cast_one,
     coe_unit_of_coprime, Units.val_pow_eq_pow_val]
 #align nat.modeq.pow_totient Nat.ModEq.pow_totient
+-/
 
 section
 
 variable {V : Type _} [Fintype K] [DivisionRing K] [AddCommGroup V] [Module K V]
 
+#print card_eq_pow_finrank /-
 -- should this go in a namespace?
 -- finite_dimensional would be natural,
 -- but we don't assume it...
@@ -393,6 +406,7 @@ theorem card_eq_pow_finrank [Fintype V] : Fintype.card V = q ^ FiniteDimensional
   let b := IsNoetherian.finsetBasis K V
   rw [Module.card_fintype b, ← FiniteDimensional.finrank_eq_card_basis b]
 #align card_eq_pow_finrank card_eq_pow_finrank
+-/
 
 end
 
@@ -493,7 +507,7 @@ theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a :=
   rw [Finite.injective_iff_surjective] at h 
   -- sq not surjective
   simp_rw [IsSquare, ← pow_two, @eq_comm _ _ (_ ^ 2)]
-  push_neg  at h ⊢
+  push_neg at h ⊢
   exact h
 #align finite_field.exists_nonsquare FiniteField.exists_nonsquare
 
@@ -501,6 +515,7 @@ end Finite
 
 variable [Fintype F]
 
+#print FiniteField.even_card_iff_char_two /-
 /-- The finite field `F` has even cardinality iff it has characteristic `2`. -/
 theorem even_card_iff_char_two : ringChar F = 2 ↔ Fintype.card F % 2 = 0 :=
   by
@@ -515,14 +530,19 @@ theorem even_card_iff_char_two : ringChar F = 2 ↔ Fintype.card F % 2 = 0 :=
     rw [Nat.even_iff, Nat.mod_mod] at hev 
     exact (Nat.Prime.eq_two_or_odd hp).resolve_right (ne_of_eq_of_ne hev zero_ne_one)
 #align finite_field.even_card_iff_char_two FiniteField.even_card_iff_char_two
+-/
 
+#print FiniteField.even_card_of_char_two /-
 theorem even_card_of_char_two (hF : ringChar F = 2) : Fintype.card F % 2 = 0 :=
   even_card_iff_char_two.mp hF
 #align finite_field.even_card_of_char_two FiniteField.even_card_of_char_two
+-/
 
+#print FiniteField.odd_card_of_char_ne_two /-
 theorem odd_card_of_char_ne_two (hF : ringChar F ≠ 2) : Fintype.card F % 2 = 1 :=
   Nat.mod_two_ne_zero.mp (mt even_card_iff_char_two.mpr hF)
 #align finite_field.odd_card_of_char_ne_two FiniteField.odd_card_of_char_ne_two
+-/
 
 /-- If `F` has odd characteristic, then for nonzero `a : F`, we have that `a ^ (#F / 2) = ±1`. -/
 theorem pow_dichotomy (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
@@ -539,25 +559,25 @@ if and only if `a ^ (#F / 2) = 1`. -/
 theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
     IsSquare a ↔ a ^ (Fintype.card F / 2) = 1 := by
   classical
-    obtain ⟨g, hg⟩ := IsCyclic.exists_generator Fˣ
-    obtain ⟨n, hn⟩ : a ∈ Submonoid.powers g := by rw [mem_powers_iff_mem_zpowers]; apply hg
-    have hodd := Nat.two_mul_odd_div_two (FiniteField.odd_card_of_char_ne_two hF)
-    constructor
-    · rintro ⟨y, rfl⟩
-      rw [← pow_two, ← pow_mul, hodd]
-      apply_fun @coe Fˣ F _ using Units.ext
-      · push_cast
-        exact FiniteField.pow_card_sub_one_eq_one (y : F) (Units.ne_zero y)
-    · subst a; intro h
-      have key : 2 * (Fintype.card F / 2) ∣ n * (Fintype.card F / 2) :=
-        by
-        rw [← pow_mul] at h 
-        rw [hodd, ← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hg]
-        apply orderOf_dvd_of_pow_eq_one h
-      have : 0 < Fintype.card F / 2 := Nat.div_pos Fintype.one_lt_card (by norm_num)
-      obtain ⟨m, rfl⟩ := Nat.dvd_of_mul_dvd_mul_right this key
-      refine' ⟨g ^ m, _⟩
-      rw [mul_comm, pow_mul, pow_two]
+  obtain ⟨g, hg⟩ := IsCyclic.exists_generator Fˣ
+  obtain ⟨n, hn⟩ : a ∈ Submonoid.powers g := by rw [mem_powers_iff_mem_zpowers]; apply hg
+  have hodd := Nat.two_mul_odd_div_two (FiniteField.odd_card_of_char_ne_two hF)
+  constructor
+  · rintro ⟨y, rfl⟩
+    rw [← pow_two, ← pow_mul, hodd]
+    apply_fun @coe Fˣ F _ using Units.ext
+    · push_cast
+      exact FiniteField.pow_card_sub_one_eq_one (y : F) (Units.ne_zero y)
+  · subst a; intro h
+    have key : 2 * (Fintype.card F / 2) ∣ n * (Fintype.card F / 2) :=
+      by
+      rw [← pow_mul] at h 
+      rw [hodd, ← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hg]
+      apply orderOf_dvd_of_pow_eq_one h
+    have : 0 < Fintype.card F / 2 := Nat.div_pos Fintype.one_lt_card (by norm_num)
+    obtain ⟨m, rfl⟩ := Nat.dvd_of_mul_dvd_mul_right this key
+    refine' ⟨g ^ m, _⟩
+    rw [mul_comm, pow_mul, pow_two]
 #align finite_field.unit_is_square_iff FiniteField.unit_isSquare_iff
 
 /-- A non-zero `a : F` is a square if and only if `a ^ (#F / 2) = 1`. -/
Diff
@@ -82,8 +82,8 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
   letI := Classical.decEq R
   suffices ¬Disjoint (univ.image fun x : R => eval x f) (univ.image fun x : R => eval x (-g))
     by
-    simp only [disjoint_left, mem_image] at this
-    push_neg  at this
+    simp only [disjoint_left, mem_image] at this 
+    push_neg  at this 
     rcases this with ⟨x, ⟨a, _, ha⟩, ⟨b, _, hb⟩⟩
     exact ⟨a, b, by rw [ha, ← hb, eval_neg, neg_add_self]⟩
   fun hd : Disjoint _ _ =>
@@ -158,17 +158,17 @@ theorem card (p : ℕ) [CharP K p] : ∃ n : ℕ+, Nat.Prime p ∧ q = p ^ (n :
   haveI hp : Fact p.prime := ⟨CharP.char_is_prime K p⟩
   letI : Module (ZMod p) K := { (ZMod.castHom dvd_rfl K : ZMod p →+* _).toModule with }
   obtain ⟨n, h⟩ := VectorSpace.card_fintype (ZMod p) K
-  rw [ZMod.card] at h
+  rw [ZMod.card] at h 
   refine' ⟨⟨n, _⟩, hp.1, h⟩
   apply Or.resolve_left (Nat.eq_zero_or_pos n)
   rintro rfl
-  rw [pow_zero] at h
+  rw [pow_zero] at h 
   have : (0 : K) = 1 := by apply fintype.card_le_one_iff.mp (le_of_eq h)
   exact absurd this zero_ne_one
 #align finite_field.card FiniteField.card
 
 -- this statement doesn't use `q` because we want `K` to be an explicit parameter
-theorem card' : ∃ (p : ℕ)(n : ℕ+), Nat.Prime p ∧ Fintype.card K = p ^ (n : ℕ) :=
+theorem card' : ∃ (p : ℕ) (n : ℕ+), Nat.Prime p ∧ Fintype.card K = p ^ (n : ℕ) :=
   let ⟨p, hc⟩ := CharP.exists K
   ⟨p, @FiniteField.card K _ _ p hc⟩
 #align finite_field.card' FiniteField.card'
@@ -193,7 +193,7 @@ theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣
     constructor
     · intro h; apply h
     · intro h y
-      simp_rw [← mem_powers_iff_mem_zpowers] at hx
+      simp_rw [← mem_powers_iff_mem_zpowers] at hx 
       rcases hx y with ⟨j, rfl⟩
       rw [← pow_mul, mul_comm, pow_mul, h, one_pow]
 #align finite_field.forall_pow_eq_one_iff FiniteField.forall_pow_eq_one_iff
@@ -206,7 +206,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
   let φ : Kˣ →* K :=
     { toFun := fun x => x ^ i
       map_one' := by rw [Units.val_one, one_pow]
-      map_mul' := by intros ; rw [Units.val_mul, mul_pow] }
+      map_mul' := by intros; rw [Units.val_mul, mul_pow] }
   have : Decidable (φ = 1) := by classical infer_instance
   calc
     (∑ x : Kˣ, φ x) = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
@@ -316,7 +316,7 @@ theorem expand_card (f : K[X]) : expand K q f = f ^ q :=
   letI := hp
   rcases FiniteField.card K p with ⟨⟨n, npos⟩, ⟨hp, hn⟩⟩
   haveI : Fact p.prime := ⟨hp⟩
-  dsimp at hn
+  dsimp at hn 
   rw [hn, ← map_expand_pow_char, frobenius_pow hn, RingHom.one_def, map_id]
 #align finite_field.expand_card FiniteField.expand_card
 
@@ -329,7 +329,7 @@ open FiniteField Polynomial
 theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p, a ^ 2 + b ^ 2 = x :=
   by
   cases' hp.1.eq_two_or_odd with hp2 hp_odd
-  · subst p; change Fin 2 at x; fin_cases x; · use 0; simp; · use 0, 1; simp
+  · subst p; change Fin 2 at x ; fin_cases x; · use 0; simp; · use 0, 1; simp
   let f : (ZMod p)[X] := X ^ 2
   let g : (ZMod p)[X] := X ^ 2 - C x
   obtain ⟨a, b, hab⟩ : ∃ a b, f.eval a + g.eval b = 0 :=
@@ -376,7 +376,7 @@ theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
   have := ZMod.pow_totient x'
-  apply_fun (coe : Units (ZMod n) → ZMod n)  at this
+  apply_fun (coe : Units (ZMod n) → ZMod n)  at this 
   simpa only [-ZMod.pow_totient, Nat.succ_eq_add_one, Nat.cast_pow, Units.val_one, Nat.cast_one,
     coe_unit_of_coprime, Units.val_pow_eq_pow_val]
 #align nat.modeq.pow_totient Nat.ModEq.pow_totient
@@ -403,7 +403,7 @@ namespace ZMod
 /-- A variation on Fermat's little theorem. See `zmod.pow_card_sub_one_eq_one` -/
 @[simp]
 theorem pow_card {p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p = x := by
-  have h := FiniteField.pow_card x; rwa [ZMod.card p] at h
+  have h := FiniteField.pow_card x; rwa [ZMod.card p] at h 
 #align zmod.pow_card ZMod.pow_card
 
 @[simp]
@@ -431,7 +431,7 @@ theorem units_pow_card_sub_one_eq_one (p : ℕ) [Fact p.Prime] (a : (ZMod p)ˣ)
 
 /-- **Fermat's Little Theorem**: for all nonzero `a : zmod p`, we have `a ^ (p - 1) = 1`. -/
 theorem pow_card_sub_one_eq_one {p : ℕ} [Fact p.Prime] {a : ZMod p} (ha : a ≠ 0) :
-    a ^ (p - 1) = 1 := by have h := pow_card_sub_one_eq_one a ha; rwa [ZMod.card p] at h
+    a ^ (p - 1) = 1 := by have h := pow_card_sub_one_eq_one a ha; rwa [ZMod.card p] at h 
 #align zmod.pow_card_sub_one_eq_one ZMod.pow_card_sub_one_eq_one
 
 theorem orderOf_units_dvd_card_sub_one {p : ℕ} [Fact p.Prime] (u : (ZMod p)ˣ) : orderOf u ∣ p - 1 :=
@@ -446,7 +446,7 @@ theorem orderOf_dvd_card_sub_one {p : ℕ} [Fact p.Prime] {a : ZMod p} (ha : a 
 open Polynomial
 
 theorem expand_card {p : ℕ} [Fact p.Prime] (f : Polynomial (ZMod p)) :
-    expand (ZMod p) p f = f ^ p := by have h := FiniteField.expand_card f; rwa [ZMod.card p] at h
+    expand (ZMod p) p f = f ^ p := by have h := FiniteField.expand_card f; rwa [ZMod.card p] at h 
 #align zmod.expand_card ZMod.expand_card
 
 end ZMod
@@ -490,10 +490,10 @@ theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a :=
     simp only [injective, not_forall, exists_prop]
     refine' ⟨-1, 1, _, Ring.neg_one_ne_one_of_char_ne_two hF⟩
     simp only [sq, one_pow, neg_one_sq]
-  rw [Finite.injective_iff_surjective] at h
+  rw [Finite.injective_iff_surjective] at h 
   -- sq not surjective
   simp_rw [IsSquare, ← pow_two, @eq_comm _ _ (_ ^ 2)]
-  push_neg  at h⊢
+  push_neg  at h ⊢
   exact h
 #align finite_field.exists_nonsquare FiniteField.exists_nonsquare
 
@@ -512,7 +512,7 @@ theorem even_card_iff_char_two : ringChar F = 2 ↔ Fintype.card F % 2 = 0 :=
     simp only [Nat.bit0_mod_two, zero_pow', Ne.def, PNat.ne_zero, not_false_iff, Nat.zero_mod]
   · rw [← Nat.even_iff, Nat.even_pow]
     rintro ⟨hev, hnz⟩
-    rw [Nat.even_iff, Nat.mod_mod] at hev
+    rw [Nat.even_iff, Nat.mod_mod] at hev 
     exact (Nat.Prime.eq_two_or_odd hp).resolve_right (ne_of_eq_of_ne hev zero_ne_one)
 #align finite_field.even_card_iff_char_two FiniteField.even_card_iff_char_two
 
@@ -530,7 +530,7 @@ theorem pow_dichotomy (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
   by
   have h₁ := FiniteField.pow_card_sub_one_eq_one a ha
   rw [← Nat.two_mul_odd_div_two (FiniteField.odd_card_of_char_ne_two hF), mul_comm, pow_mul,
-    pow_two] at h₁
+    pow_two] at h₁ 
   exact mul_self_eq_one_iff.mp h₁
 #align finite_field.pow_dichotomy FiniteField.pow_dichotomy
 
@@ -551,7 +551,7 @@ theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
     · subst a; intro h
       have key : 2 * (Fintype.card F / 2) ∣ n * (Fintype.card F / 2) :=
         by
-        rw [← pow_mul] at h
+        rw [← pow_mul] at h 
         rw [hodd, ← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hg]
         apply orderOf_dvd_of_pow_eq_one h
       have : 0 < Fintype.card F / 2 := Nat.div_pos Fintype.one_lt_card (by norm_num)
Diff
@@ -4,12 +4,11 @@ Released under Apache 2.0 license as described in the file LICENSE.
 Authors: Chris Hughes, Joey van Langen, Casper Putz
 
 ! This file was ported from Lean 3 source module field_theory.finite.basic
-! leanprover-community/mathlib commit 2196ab363eb097c008d4497125e0dde23fb36db2
+! leanprover-community/mathlib commit 12a85fac627bea918960da036049d611b1a3ee43
 ! Please do not edit these lines, except to modify the commit id
 ! if you have ported upstream changes.
 -/
 import Mathbin.FieldTheory.Separable
-import Mathbin.FieldTheory.SplittingField
 import Mathbin.RingTheory.IntegralDomain
 import Mathbin.Tactic.ApplyFun
 
@@ -246,8 +245,6 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
       
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 
-section IsSplittingField
-
 open Polynomial
 
 section
@@ -302,22 +299,6 @@ theorem roots_x_pow_card_sub_x : roots (X ^ q - X : K[X]) = Finset.univ.val := b
         MulZeroClass.zero_mul, zero_sub]
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_x_pow_card_sub_x
 
-instance (F : Type _) [Field F] [Algebra F K] : IsSplittingField F K (X ^ q - X)
-    where
-  Splits :=
-    by
-    have h : (X ^ q - X : K[X]).natDegree = q :=
-      X_pow_card_sub_X_nat_degree_eq K Fintype.one_lt_card
-    rw [← splits_id_iff_splits, splits_iff_card_roots, Polynomial.map_sub, Polynomial.map_pow,
-      map_X, h, roots_X_pow_card_sub_X K, ← Finset.card_def, Finset.card_univ]
-  adjoin_roots := by
-    classical
-      trans Algebra.adjoin F ((roots (X ^ q - X : K[X])).toFinset : Set K)
-      · simp only [Polynomial.map_pow, map_X, Polynomial.map_sub]
-      · rw [roots_X_pow_card_sub_X, val_to_finset, coe_univ, Algebra.adjoin_univ]
-
-end IsSplittingField
-
 variable {K}
 
 theorem frobenius_pow {p : ℕ} [Fact p.Prime] [CharP K p] {n : ℕ} (hcard : q = p ^ n) :
Diff
@@ -54,7 +54,7 @@ local notation "q" => Fintype.card K
 
 open Finset Function
 
-open BigOperators Polynomial
+open scoped BigOperators Polynomial
 
 namespace FiniteField
 
@@ -374,7 +374,7 @@ theorem sq_add_sq (R : Type _) [CommRing R] [IsDomain R] (p : ℕ) [NeZero p] [C
 
 end CharP
 
-open Nat
+open scoped Nat
 
 open ZMod
 
Diff
@@ -138,9 +138,7 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 :=
 theorem pow_card (a : K) : a ^ q = a :=
   by
   have hp : 0 < Fintype.card K := lt_trans zero_lt_one Fintype.one_lt_card
-  by_cases h : a = 0;
-  · rw [h]
-    apply zero_pow hp
+  by_cases h : a = 0; · rw [h]; apply zero_pow hp
   rw [← Nat.succ_pred_eq_of_pos hp, pow_succ, Nat.pred_eq_sub_one, pow_card_sub_one_eq_one a h,
     mul_one]
 #align finite_field.pow_card FiniteField.pow_card
@@ -194,8 +192,7 @@ theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣
     rw [← Fintype.card_units, ← orderOf_eq_card_of_forall_mem_zpowers hx,
       orderOf_dvd_iff_pow_eq_one]
     constructor
-    · intro h
-      apply h
+    · intro h; apply h
     · intro h y
       simp_rw [← mem_powers_iff_mem_zpowers] at hx
       rcases hx y with ⟨j, rfl⟩
@@ -210,9 +207,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
   let φ : Kˣ →* K :=
     { toFun := fun x => x ^ i
       map_one' := by rw [Units.val_one, one_pow]
-      map_mul' := by
-        intros
-        rw [Units.val_mul, mul_pow] }
+      map_mul' := by intros ; rw [Units.val_mul, mul_pow] }
   have : Decidable (φ = 1) := by classical infer_instance
   calc
     (∑ x : Kˣ, φ x) = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
@@ -220,15 +215,11 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
     
   suffices q - 1 ∣ i ↔ φ = 1 by
     simp only [this]
-    split_ifs with h h
-    swap
-    rfl
+    split_ifs with h h; swap; rfl
     rw [Fintype.card_units, Nat.cast_sub, cast_card_eq_zero, Nat.cast_one, zero_sub]
-    show 1 ≤ q
-    exact fintype.card_pos_iff.mpr ⟨0⟩
+    show 1 ≤ q; exact fintype.card_pos_iff.mpr ⟨0⟩
   rw [← forall_pow_eq_one_iff, MonoidHom.ext_iff]
-  apply forall_congr'
-  intro x
+  apply forall_congr'; intro x
   rw [Units.ext_iff, Units.val_pow_eq_pow_val, Units.val_one, MonoidHom.one_apply]
   rfl
 #align finite_field.sum_pow_units FiniteField.sum_pow_units
@@ -240,9 +231,7 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
   by_cases hi : i = 0
   · simp only [hi, nsmul_one, sum_const, pow_zero, card_univ, cast_card_eq_zero]
   classical
-    have hiq : ¬q - 1 ∣ i := by
-      contrapose! h
-      exact Nat.le_of_dvd (Nat.pos_of_ne_zero hi) h
+    have hiq : ¬q - 1 ∣ i := by contrapose! h; exact Nat.le_of_dvd (Nat.pos_of_ne_zero hi) h
     let φ : Kˣ ↪ K := ⟨coe, Units.ext⟩
     have : univ.map φ = univ \ {0} := by
       ext x
@@ -252,12 +241,8 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
       (∑ x : K, x ^ i) = ∑ x in univ \ {(0 : K)}, x ^ i := by
         rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton,
           zero_pow (Nat.pos_of_ne_zero hi), add_zero]
-      _ = ∑ x : Kˣ, x ^ i := by
-        rw [← this, univ.sum_map φ]
-        rfl
-      _ = 0 := by
-        rw [sum_pow_units K i, if_neg]
-        exact hiq
+      _ = ∑ x : Kˣ, x ^ i := by rw [← this, univ.sum_map φ]; rfl
+      _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
       
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 
@@ -363,13 +348,7 @@ open FiniteField Polynomial
 theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p, a ^ 2 + b ^ 2 = x :=
   by
   cases' hp.1.eq_two_or_odd with hp2 hp_odd
-  · subst p
-    change Fin 2 at x
-    fin_cases x
-    · use 0
-      simp
-    · use 0, 1
-      simp
+  · subst p; change Fin 2 at x; fin_cases x; · use 0; simp; · use 0, 1; simp
   let f : (ZMod p)[X] := X ^ 2
   let g : (ZMod p)[X] := X ^ 2 - C x
   obtain ⟨a, b, hab⟩ : ∃ a b, f.eval a + g.eval b = 0 :=
@@ -442,10 +421,8 @@ namespace ZMod
 
 /-- A variation on Fermat's little theorem. See `zmod.pow_card_sub_one_eq_one` -/
 @[simp]
-theorem pow_card {p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p = x :=
-  by
-  have h := FiniteField.pow_card x
-  rwa [ZMod.card p] at h
+theorem pow_card {p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p = x := by
+  have h := FiniteField.pow_card x; rwa [ZMod.card p] at h
 #align zmod.pow_card ZMod.pow_card
 
 @[simp]
@@ -457,9 +434,7 @@ theorem pow_card_pow {n p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p ^ n = x :=
 #align zmod.pow_card_pow ZMod.pow_card_pow
 
 @[simp]
-theorem frobenius_zMod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom.id _ :=
-  by
-  ext a
+theorem frobenius_zMod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom.id _ := by ext a;
   rw [frobenius_def, ZMod.pow_card, RingHom.id_apply]
 #align zmod.frobenius_zmod ZMod.frobenius_zMod
 
@@ -475,9 +450,7 @@ theorem units_pow_card_sub_one_eq_one (p : ℕ) [Fact p.Prime] (a : (ZMod p)ˣ)
 
 /-- **Fermat's Little Theorem**: for all nonzero `a : zmod p`, we have `a ^ (p - 1) = 1`. -/
 theorem pow_card_sub_one_eq_one {p : ℕ} [Fact p.Prime] {a : ZMod p} (ha : a ≠ 0) :
-    a ^ (p - 1) = 1 := by
-  have h := pow_card_sub_one_eq_one a ha
-  rwa [ZMod.card p] at h
+    a ^ (p - 1) = 1 := by have h := pow_card_sub_one_eq_one a ha; rwa [ZMod.card p] at h
 #align zmod.pow_card_sub_one_eq_one ZMod.pow_card_sub_one_eq_one
 
 theorem orderOf_units_dvd_card_sub_one {p : ℕ} [Fact p.Prime] (u : (ZMod p)ˣ) : orderOf u ∣ p - 1 :=
@@ -492,10 +465,7 @@ theorem orderOf_dvd_card_sub_one {p : ℕ} [Fact p.Prime] {a : ZMod p} (ha : a 
 open Polynomial
 
 theorem expand_card {p : ℕ} [Fact p.Prime] (f : Polynomial (ZMod p)) :
-    expand (ZMod p) p f = f ^ p :=
-  by
-  have h := FiniteField.expand_card f
-  rwa [ZMod.card p] at h
+    expand (ZMod p) p f = f ^ p := by have h := FiniteField.expand_card f; rwa [ZMod.card p] at h
 #align zmod.expand_card ZMod.expand_card
 
 end ZMod
@@ -589,10 +559,7 @@ theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
     IsSquare a ↔ a ^ (Fintype.card F / 2) = 1 := by
   classical
     obtain ⟨g, hg⟩ := IsCyclic.exists_generator Fˣ
-    obtain ⟨n, hn⟩ : a ∈ Submonoid.powers g :=
-      by
-      rw [mem_powers_iff_mem_zpowers]
-      apply hg
+    obtain ⟨n, hn⟩ : a ∈ Submonoid.powers g := by rw [mem_powers_iff_mem_zpowers]; apply hg
     have hodd := Nat.two_mul_odd_div_two (FiniteField.odd_card_of_char_ne_two hF)
     constructor
     · rintro ⟨y, rfl⟩
@@ -600,8 +567,7 @@ theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
       apply_fun @coe Fˣ F _ using Units.ext
       · push_cast
         exact FiniteField.pow_card_sub_one_eq_one (y : F) (Units.ne_zero y)
-    · subst a
-      intro h
+    · subst a; intro h
       have key : 2 * (Fintype.card F / 2) ∣ n * (Fintype.card F / 2) :=
         by
         rw [← pow_mul] at h
@@ -621,14 +587,10 @@ theorem isSquare_iff (hF : ringChar F ≠ 2) {a : F} (ha : a ≠ 0) :
     (iff_congr _ (by simp [Units.ext_iff])).mp (FiniteField.unit_isSquare_iff hF (Units.mk0 a ha))
   simp only [IsSquare, Units.ext_iff, Units.val_mk0, Units.val_mul]
   constructor
-  · rintro ⟨y, hy⟩
-    exact ⟨y, hy⟩
+  · rintro ⟨y, hy⟩; exact ⟨y, hy⟩
   · rintro ⟨y, rfl⟩
-    have hy : y ≠ 0 := by
-      rintro rfl
-      simpa [zero_pow] using ha
-    refine' ⟨Units.mk0 y hy, _⟩
-    simp
+    have hy : y ≠ 0 := by rintro rfl; simpa [zero_pow] using ha
+    refine' ⟨Units.mk0 y hy, _⟩; simp
 #align finite_field.is_square_iff FiniteField.isSquare_iff
 
 end FiniteField
Diff
@@ -510,7 +510,7 @@ theorem Int.ModEq.pow_card_sub_one_eq_one {p : ℕ} (hp : Nat.Prime p) {n : ℤ}
     rw [CharP.int_cast_eq_zero_iff _ p, ← (nat.prime_iff_prime_int.mp hp).coprime_iff_not_dvd]
     · exact hpn.symm
     exact ZMod.charP p
-  simpa [← ZMod.int_coe_eq_int_coe_iff] using ZMod.pow_card_sub_one_eq_one this
+  simpa [← ZMod.int_cast_eq_int_cast_iff] using ZMod.pow_card_sub_one_eq_one this
 #align int.modeq.pow_card_sub_one_eq_one Int.ModEq.pow_card_sub_one_eq_one
 
 section
Diff
@@ -526,7 +526,7 @@ variable [Finite F]
 /-- In a finite field of characteristic `2`, all elements are squares. -/
 theorem isSquare_of_char_two (hF : ringChar F = 2) (a : F) : IsSquare a :=
   haveI hF' : CharP F 2 := ringChar.of_eq hF
-  isSquare_of_char_two' a
+  isSquare_of_charTwo' a
 #align finite_field.is_square_of_char_two FiniteField.isSquare_of_char_two
 
 /-- In a finite field of odd characteristic, not every element is a square. -/
Diff
@@ -4,7 +4,7 @@ Released under Apache 2.0 license as described in the file LICENSE.
 Authors: Chris Hughes, Joey van Langen, Casper Putz
 
 ! This file was ported from Lean 3 source module field_theory.finite.basic
-! leanprover-community/mathlib commit 55d224c38461be1e8e4363247dd110137c24a4ff
+! leanprover-community/mathlib commit 2196ab363eb097c008d4497125e0dde23fb36db2
 ! Please do not edit these lines, except to modify the commit id
 ! if you have ported upstream changes.
 -/
@@ -116,7 +116,7 @@ theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
     have : (∏ x in (@univ Kˣ _).eraseₓ (-1), x) = 1 :=
       prod_involution (fun x _ => x⁻¹) (by simp)
         (fun a => by simp (config := { contextual := true }) [Units.inv_eq_self_iff])
-        (fun a => by simp [@inv_eq_iff_inv_eq _ _ a, eq_comm]) (by simp)
+        (fun a => by simp [@inv_eq_iff_eq_inv _ _ a]) (by simp)
     rw [← insert_erase (mem_univ (-1 : Kˣ)), prod_insert (not_mem_erase _ _), this, mul_one]
 #align finite_field.prod_univ_units_id_eq_neg_one FiniteField.prod_univ_units_id_eq_neg_one
 
Diff
@@ -313,8 +313,8 @@ theorem roots_x_pow_card_sub_x : roots (X ^ q - X : K[X]) = Finset.univ.val := b
     rw [separable_def]
     convert is_coprime_one_right.neg_right using 1
     ·
-      rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0, zero_mul,
-        zero_sub]
+      rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
+        MulZeroClass.zero_mul, zero_sub]
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_x_pow_card_sub_x
 
 instance (F : Type _) [Field F] [Algebra F K] : IsSplittingField F K (X ^ q - X)
Diff
@@ -70,9 +70,9 @@ theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp :
     Fintype.card R ≤ natDegree p * (univ.image fun x => eval x p).card :=
   Finset.card_le_mul_card_image _ _ fun a _ =>
     calc
-      _ = (p - c a).roots.toFinset.card :=
+      _ = (p - C a).roots.toFinset.card :=
         congr_arg card (by simp [Finset.ext_iff, mem_roots_sub_C hp])
-      _ ≤ (p - c a).roots.card := (Multiset.toFinset_card_le _)
+      _ ≤ (p - C a).roots.card := (Multiset.toFinset_card_le _)
       _ ≤ _ := card_roots_sub_C' hp
       
 #align finite_field.card_image_polynomial_eval FiniteField.card_image_polynomial_eval
@@ -269,7 +269,7 @@ section
 
 variable (K' : Type _) [Field K'] {p n : ℕ}
 
-theorem x_pow_card_sub_x_natDegree_eq (hp : 1 < p) : (x ^ p - x : K'[X]).natDegree = p :=
+theorem x_pow_card_sub_x_natDegree_eq (hp : 1 < p) : (X ^ p - X : K'[X]).natDegree = p :=
   by
   have h1 : (X : K'[X]).degree < (X ^ p : K'[X]).degree :=
     by
@@ -279,11 +279,11 @@ theorem x_pow_card_sub_x_natDegree_eq (hp : 1 < p) : (x ^ p - x : K'[X]).natDegr
 #align finite_field.X_pow_card_sub_X_nat_degree_eq FiniteField.x_pow_card_sub_x_natDegree_eq
 
 theorem x_pow_card_pow_sub_x_natDegree_eq (hn : n ≠ 0) (hp : 1 < p) :
-    (x ^ p ^ n - x : K'[X]).natDegree = p ^ n :=
+    (X ^ p ^ n - X : K'[X]).natDegree = p ^ n :=
   x_pow_card_sub_x_natDegree_eq K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
 #align finite_field.X_pow_card_pow_sub_X_nat_degree_eq FiniteField.x_pow_card_pow_sub_x_natDegree_eq
 
-theorem x_pow_card_sub_x_ne_zero (hp : 1 < p) : (x ^ p - x : K'[X]) ≠ 0 :=
+theorem x_pow_card_sub_x_ne_zero (hp : 1 < p) : (X ^ p - X : K'[X]) ≠ 0 :=
   ne_zero_of_natDegree_gt <|
     calc
       1 < _ := hp
@@ -291,7 +291,7 @@ theorem x_pow_card_sub_x_ne_zero (hp : 1 < p) : (x ^ p - x : K'[X]) ≠ 0 :=
       
 #align finite_field.X_pow_card_sub_X_ne_zero FiniteField.x_pow_card_sub_x_ne_zero
 
-theorem x_pow_card_pow_sub_x_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (x ^ p ^ n - x : K'[X]) ≠ 0 :=
+theorem x_pow_card_pow_sub_x_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (X ^ p ^ n - X : K'[X]) ≠ 0 :=
   x_pow_card_sub_x_ne_zero K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
 #align finite_field.X_pow_card_pow_sub_X_ne_zero FiniteField.x_pow_card_pow_sub_x_ne_zero
 
@@ -299,7 +299,7 @@ end
 
 variable (p : ℕ) [Fact p.Prime] [Algebra (ZMod p) K]
 
-theorem roots_x_pow_card_sub_x : roots (x ^ q - x : K[X]) = Finset.univ.val := by
+theorem roots_x_pow_card_sub_x : roots (X ^ q - X : K[X]) = Finset.univ.val := by
   classical
     have aux : (X ^ q - X : K[X]) ≠ 0 := X_pow_card_sub_X_ne_zero K Fintype.one_lt_card
     have : (roots (X ^ q - X : K[X])).toFinset = Finset.univ :=
@@ -317,7 +317,7 @@ theorem roots_x_pow_card_sub_x : roots (x ^ q - x : K[X]) = Finset.univ.val := b
         zero_sub]
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_x_pow_card_sub_x
 
-instance (F : Type _) [Field F] [Algebra F K] : IsSplittingField F K (x ^ q - x)
+instance (F : Type _) [Field F] [Algebra F K] : IsSplittingField F K (X ^ q - X)
     where
   Splits :=
     by
Diff
@@ -72,7 +72,7 @@ theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp :
     calc
       _ = (p - c a).roots.toFinset.card :=
         congr_arg card (by simp [Finset.ext_iff, mem_roots_sub_C hp])
-      _ ≤ (p - c a).roots.card := Multiset.toFinset_card_le _
+      _ ≤ (p - c a).roots.card := (Multiset.toFinset_card_le _)
       _ ≤ _ := card_roots_sub_C' hp
       
 #align finite_field.card_image_polynomial_eval FiniteField.card_image_polynomial_eval
@@ -93,14 +93,14 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
       2 * ((univ.image fun x : R => eval x f) ∪ univ.image fun x : R => eval x (-g)).card ≤
           2 * Fintype.card R :=
         Nat.mul_le_mul_left _ (Finset.card_le_univ _)
-      _ = Fintype.card R + Fintype.card R := two_mul _
+      _ = Fintype.card R + Fintype.card R := (two_mul _)
       _ <
           nat_degree f * (univ.image fun x : R => eval x f).card +
             nat_degree (-g) * (univ.image fun x : R => eval x (-g)).card :=
-        add_lt_add_of_lt_of_le
+        (add_lt_add_of_lt_of_le
           (lt_of_le_of_ne (card_image_polynomial_eval (by rw [hf2] <;> exact by decide))
             (mt (congr_arg (· % 2)) (by simp [nat_degree_eq_of_degree_eq_some hf2, hR])))
-          (card_image_polynomial_eval (by rw [degree_neg, hg2] <;> exact by decide))
+          (card_image_polynomial_eval (by rw [degree_neg, hg2] <;> exact by decide)))
       _ = 2 * ((univ.image fun x : R => eval x f) ∪ univ.image fun x : R => eval x (-g)).card := by
         rw [card_disjoint_union hd] <;>
           simp [nat_degree_eq_of_degree_eq_some hf2, nat_degree_eq_of_degree_eq_some hg2, bit0,

Changes in mathlib4

mathlib3
mathlib4
chore: Rename nat_cast/int_cast/rat_cast to natCast/intCast/ratCast (#11486)

Now that I am defining NNRat.cast, I want a definitive answer to this naming issue. Plenty of lemmas in mathlib already use natCast/intCast/ratCast over nat_cast/int_cast/rat_cast, and this matches with the general expectation that underscore-separated name parts correspond to a single declaration.

Diff
@@ -427,7 +427,7 @@ theorem Nat.sq_add_sq_zmodEq (p : ℕ) [Fact p.Prime] (x : ℤ) :
     ZMod.natAbs_valMinAbs_le _, ?_⟩
   rw [← a.coe_valMinAbs, ← b.coe_valMinAbs] at hx
   push_cast
-  rw [sq_abs, sq_abs, ← ZMod.int_cast_eq_int_cast_iff]
+  rw [sq_abs, sq_abs, ← ZMod.intCast_eq_intCast_iff]
   exact mod_cast hx
 
 /-- If `p` is a prime natural number and `x` is a natural number, then there exist natural numbers
@@ -555,9 +555,9 @@ theorem Int.ModEq.pow_card_sub_one_eq_one {p : ℕ} (hp : Nat.Prime p) {n : ℤ}
     n ^ (p - 1) ≡ 1 [ZMOD p] := by
   haveI : Fact p.Prime := ⟨hp⟩
   have : ¬(n : ZMod p) = 0 := by
-    rw [CharP.int_cast_eq_zero_iff _ p, ← (Nat.prime_iff_prime_int.mp hp).coprime_iff_not_dvd]
+    rw [CharP.intCast_eq_zero_iff _ p, ← (Nat.prime_iff_prime_int.mp hp).coprime_iff_not_dvd]
     · exact hpn.symm
-  simpa [← ZMod.int_cast_eq_int_cast_iff] using ZMod.pow_card_sub_one_eq_one this
+  simpa [← ZMod.intCast_eq_intCast_iff] using ZMod.pow_card_sub_one_eq_one this
 #align int.modeq.pow_card_sub_one_eq_one Int.ModEq.pow_card_sub_one_eq_one
 
 section
chore: superfluous parentheses part 2 (#12131)

Co-authored-by: Moritz Firsching <firsching@google.com>

Diff
@@ -68,7 +68,7 @@ theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp :
     calc
       _ = (p - C a).roots.toFinset.card :=
         congr_arg card (by simp [Finset.ext_iff, ← mem_roots_sub_C hp])
-      _ ≤ Multiset.card (p - C a).roots := (Multiset.toFinset_card_le _)
+      _ ≤ Multiset.card (p - C a).roots := Multiset.toFinset_card_le _
       _ ≤ _ := card_roots_sub_C' hp)
 #align finite_field.card_image_polynomial_eval FiniteField.card_image_polynomial_eval
 
@@ -86,7 +86,7 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
   lt_irrefl (2 * ((univ.image fun x : R => eval x f) ∪ univ.image fun x : R => eval x (-g)).card) <|
     calc 2 * ((univ.image fun x : R => eval x f) ∪ univ.image fun x : R => eval x (-g)).card
         ≤ 2 * Fintype.card R := Nat.mul_le_mul_left _ (Finset.card_le_univ _)
-      _ = Fintype.card R + Fintype.card R := (two_mul _)
+      _ = Fintype.card R + Fintype.card R := two_mul _
       _ < natDegree f * (univ.image fun x : R => eval x f).card +
             natDegree (-g) * (univ.image fun x : R => eval x (-g)).card :=
         (add_lt_add_of_lt_of_le
chore: exact by decide -> decide (#12067)

Co-authored-by: Mario Carneiro <di.gama@gmail.com>

Diff
@@ -90,9 +90,9 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
       _ < natDegree f * (univ.image fun x : R => eval x f).card +
             natDegree (-g) * (univ.image fun x : R => eval x (-g)).card :=
         (add_lt_add_of_lt_of_le
-          (lt_of_le_of_ne (card_image_polynomial_eval (by rw [hf2]; exact by decide))
+          (lt_of_le_of_ne (card_image_polynomial_eval (by rw [hf2]; decide))
             (mt (congr_arg (· % 2)) (by simp [natDegree_eq_of_degree_eq_some hf2, hR])))
-          (card_image_polynomial_eval (by rw [degree_neg, hg2]; exact by decide)))
+          (card_image_polynomial_eval (by rw [degree_neg, hg2]; decide)))
       _ = 2 * ((univ.image fun x : R => eval x f) ∪ univ.image fun x : R => eval x (-g)).card := by
         rw [card_union_of_disjoint hd];
           simp [natDegree_eq_of_degree_eq_some hf2, natDegree_eq_of_degree_eq_some hg2, mul_add]
chore: rename IsRoot.definition back to IsRoot.def (#11999)

Co-authored-by: Scott Morrison <scott.morrison@gmail.com>

Diff
@@ -359,7 +359,7 @@ theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := b
     have : (roots (X ^ q - X : K[X])).toFinset = Finset.univ := by
       rw [eq_univ_iff_forall]
       intro x
-      rw [Multiset.mem_toFinset, mem_roots aux, IsRoot.definition, eval_sub, eval_pow, eval_X,
+      rw [Multiset.mem_toFinset, mem_roots aux, IsRoot.def, eval_sub, eval_pow, eval_X,
         sub_eq_zero, pow_card]
     rw [← this, Multiset.toFinset_val, eq_comm, Multiset.dedup_eq_self]
     apply nodup_roots
chore: remove mathport name: <expression> lines (#11928)

Quoting [@digama0](https://github.com/digama0):

These were actually never meant to go in the file, they are basically debugging information and only useful on significantly broken mathport files. You can safely remove all of them.

Diff
@@ -46,7 +46,6 @@ diamonds, as `Fintype` carries data.
 
 variable {K : Type*} {R : Type*}
 
--- mathport name: exprq
 local notation "q" => Fintype.card K
 
 open Finset
chore(Data/Int): Rename coe_nat to natCast (#11637)

Reduce the diff of #11499

Renames

All in the Int namespace:

  • ofNat_eq_castofNat_eq_natCast
  • cast_eq_cast_iff_NatnatCast_inj
  • natCast_eq_ofNatofNat_eq_natCast
  • coe_nat_subnatCast_sub
  • coe_nat_nonnegnatCast_nonneg
  • sign_coe_add_onesign_natCast_add_one
  • nat_succ_eq_int_succnatCast_succ
  • succ_neg_nat_succsucc_neg_natCast_succ
  • coe_pred_of_posnatCast_pred_of_pos
  • coe_nat_divnatCast_div
  • coe_nat_edivnatCast_ediv
  • sign_coe_nat_of_nonzerosign_natCast_of_ne_zero
  • toNat_coe_nattoNat_natCast
  • toNat_coe_nat_add_onetoNat_natCast_add_one
  • coe_nat_dvdnatCast_dvd_natCast
  • coe_nat_dvd_leftnatCast_dvd
  • coe_nat_dvd_rightdvd_natCast
  • le_coe_nat_suble_natCast_sub
  • succ_coe_nat_possucc_natCast_pos
  • coe_nat_modEq_iffnatCast_modEq_iff
  • coe_natAbsnatCast_natAbs
  • coe_nat_eq_zeronatCast_eq_zero
  • coe_nat_ne_zeronatCast_ne_zero
  • coe_nat_ne_zero_iff_posnatCast_ne_zero_iff_pos
  • abs_coe_natabs_natCast
  • coe_nat_nonpos_iffnatCast_nonpos_iff

Also rename Nat.coe_nat_dvd to Nat.cast_dvd_cast

Diff
@@ -436,7 +436,7 @@ theorem Nat.sq_add_sq_zmodEq (p : ℕ) [Fact p.Prime] (x : ℤ) :
 `ZMod.sq_add_sq` with estimates on `a` and `b`. -/
 theorem Nat.sq_add_sq_modEq (p : ℕ) [Fact p.Prime] (x : ℕ) :
     ∃ a b : ℕ, a ≤ p / 2 ∧ b ≤ p / 2 ∧ a ^ 2 + b ^ 2 ≡ x [MOD p] := by
-  simpa only [← Int.coe_nat_modEq_iff] using Nat.sq_add_sq_zmodEq p x
+  simpa only [← Int.natCast_modEq_iff] using Nat.sq_add_sq_zmodEq p x
 
 namespace CharP
 
change the order of operation in zsmulRec and nsmulRec (#11451)

We change the following field in the definition of an additive commutative monoid:

 nsmul_succ : ∀ (n : ℕ) (x : G),
-  AddMonoid.nsmul (n + 1) x = x + AddMonoid.nsmul n x
+  AddMonoid.nsmul (n + 1) x = AddMonoid.nsmul n x + x

where the latter is more natural

We adjust the definitions of ^ in monoids, groups, etc. Originally there was a warning comment about why this natural order was preferred

use x * npowRec n x and not npowRec n x * x in the definition to make sure that definitional unfolding of npowRec is blocked, to avoid deep recursion issues.

but it seems to no longer apply.

Remarks on the PR :

  • pow_succ and pow_succ' have switched their meanings.
  • Most of the time, the proofs were adjusted by priming/unpriming one lemma, or exchanging left and right; a few proofs were more complicated to adjust.
  • In particular, [Mathlib/NumberTheory/RamificationInertia.lean] used Ideal.IsPrime.mul_mem_pow which is defined in [Mathlib/RingTheory/DedekindDomain/Ideal.lean]. Changing the order of operation forced me to add the symmetric lemma Ideal.IsPrime.mem_pow_mul.
  • the docstring for Cauchy condensation test in [Mathlib/Analysis/PSeries.lean] was mathematically incorrect, I added the mention that the function is antitone.
Diff
@@ -226,7 +226,7 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 := by
 theorem pow_card (a : K) : a ^ q = a := by
   by_cases h : a = 0; · rw [h]; apply zero_pow Fintype.card_ne_zero
   rw [← Nat.succ_pred_eq_of_pos Fintype.card_pos, pow_succ, Nat.pred_eq_sub_one,
-    pow_card_sub_one_eq_one a h, mul_one]
+    pow_card_sub_one_eq_one a h, one_mul]
 #align finite_field.pow_card FiniteField.pow_card
 
 theorem pow_card_pow (n : ℕ) (a : K) : a ^ q ^ n = a := by
@@ -379,7 +379,7 @@ theorem frobenius_pow {p : ℕ} [Fact p.Prime] [CharP K p] {n : ℕ} (hcard : q
   clear hcard
   induction' n with n hn
   · simp
-  · rw [pow_succ, pow_succ', pow_mul, RingHom.mul_def, RingHom.comp_apply, frobenius_def, hn]
+  · rw [pow_succ', pow_succ, pow_mul, RingHom.mul_def, RingHom.comp_apply, frobenius_def, hn]
 #align finite_field.frobenius_pow FiniteField.frobenius_pow
 
 open Polynomial
chore(Data/Nat): Use Std lemmas (#11661)

Move basic Nat lemmas from Data.Nat.Order.Basic and Data.Nat.Pow to Data.Nat.Defs. Most proofs need adapting, but that's easily solved by replacing the general mathlib lemmas by the new Std Nat-specific lemmas and using omega.

Other changes

  • Move the last few lemmas left in Data.Nat.Pow to Algebra.GroupPower.Order
  • Move the deprecated aliases from Data.Nat.Pow to Algebra.GroupPower.Order
  • Move the bit/bit0/bit1 lemmas from Data.Nat.Order.Basic to Data.Nat.Bits
  • Fix some fallout from not importing Data.Nat.Order.Basic anymore
  • Add a few Nat-specific lemmas to help fix the fallout (look for nolint simpNF)
  • Turn Nat.mul_self_le_mul_self_iff and Nat.mul_self_lt_mul_self_iff around (they were misnamed)
  • Make more arguments to Nat.one_lt_pow implicit
Diff
@@ -333,7 +333,7 @@ set_option linter.uppercaseLean3 false in
 
 theorem X_pow_card_pow_sub_X_natDegree_eq (hn : n ≠ 0) (hp : 1 < p) :
     (X ^ p ^ n - X : K'[X]).natDegree = p ^ n :=
-  X_pow_card_sub_X_natDegree_eq K' <| Nat.one_lt_pow _ _ hn hp
+  X_pow_card_sub_X_natDegree_eq K' <| Nat.one_lt_pow hn hp
 set_option linter.uppercaseLean3 false in
 #align finite_field.X_pow_card_pow_sub_X_nat_degree_eq FiniteField.X_pow_card_pow_sub_X_natDegree_eq
 
@@ -346,7 +346,7 @@ set_option linter.uppercaseLean3 false in
 #align finite_field.X_pow_card_sub_X_ne_zero FiniteField.X_pow_card_sub_X_ne_zero
 
 theorem X_pow_card_pow_sub_X_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (X ^ p ^ n - X : K'[X]) ≠ 0 :=
-  X_pow_card_sub_X_ne_zero K' <| Nat.one_lt_pow _ _ hn hp
+  X_pow_card_sub_X_ne_zero K' <| Nat.one_lt_pow hn hp
 set_option linter.uppercaseLean3 false in
 #align finite_field.X_pow_card_pow_sub_X_ne_zero FiniteField.X_pow_card_pow_sub_X_ne_zero
 
chore: avoid some unused variables (#11594)

These will be caught by the linter in a future lean version.

Diff
@@ -204,13 +204,10 @@ theorem sum_subgroup_pow_eq_zero [CommRing K] [NoZeroDivisors K]
                   * (Multiset.map (fun i : G => (i.val : K) ^ k) Finset.univ.val).sum = 0 := by
     rw [sub_mul, mul_comm, ← h_multiset_map_sum, one_mul, sub_self]
   rw [mul_eq_zero] at hzero
-  rcases hzero with h | h
-  · contrapose! ha
-    ext
-    rw [← sub_eq_zero]
-    simp_rw [SubmonoidClass.coe_pow, Units.val_pow_eq_pow_val, OneMemClass.coe_one,
-      Units.val_one, h]
-  · exact h
+  refine hzero.resolve_left fun h => ha ?_
+  ext
+  rw [← sub_eq_zero]
+  simp_rw [SubmonoidClass.coe_pow, Units.val_pow_eq_pow_val, OneMemClass.coe_one, Units.val_one, h]
 
 section
 
chore: rename away from 'def' (#11548)

This will become an error in 2024-03-16 nightly, possibly not permanently.

Co-authored-by: Scott Morrison <scott@tqft.net>

Diff
@@ -363,7 +363,7 @@ theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := b
     have : (roots (X ^ q - X : K[X])).toFinset = Finset.univ := by
       rw [eq_univ_iff_forall]
       intro x
-      rw [Multiset.mem_toFinset, mem_roots aux, IsRoot.def, eval_sub, eval_pow, eval_X,
+      rw [Multiset.mem_toFinset, mem_roots aux, IsRoot.definition, eval_sub, eval_pow, eval_X,
         sub_eq_zero, pow_card]
     rw [← this, Multiset.toFinset_val, eq_comm, Multiset.dedup_eq_self]
     apply nodup_roots
style: homogenise porting notes (#11145)

Homogenises porting notes via capitalisation and addition of whitespace.

It makes the following changes:

  • converts "--porting note" into "-- Porting note";
  • converts "porting note" into "Porting note".
Diff
@@ -261,7 +261,7 @@ theorem card' : ∃ (p : ℕ) (n : ℕ+), Nat.Prime p ∧ Fintype.card K = p ^ (
   ⟨p, @FiniteField.card K _ _ p hc⟩
 #align finite_field.card' FiniteField.card'
 
---Porting note: this was a `simp` lemma with a 5 lines proof.
+-- Porting note: this was a `simp` lemma with a 5 lines proof.
 theorem cast_card_eq_zero : (q : K) = 0 := by
   simp
 #align finite_field.cast_card_eq_zero FiniteField.cast_card_eq_zero
@@ -519,7 +519,7 @@ theorem frobenius_zmod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom
   rw [frobenius_def, ZMod.pow_card, RingHom.id_apply]
 #align zmod.frobenius_zmod ZMod.frobenius_zmod
 
---Porting note: this was a `simp` lemma, but now the LHS simplify to `φ p`.
+-- Porting note: this was a `simp` lemma, but now the LHS simplify to `φ p`.
 theorem card_units (p : ℕ) [Fact p.Prime] : Fintype.card (ZMod p)ˣ = p - 1 := by
   rw [Fintype.card_units, card]
 #align zmod.card_units ZMod.card_units
chore: prepare Lean version bump with explicit simp (#10999)

Co-authored-by: Scott Morrison <scott.morrison@gmail.com>

Diff
@@ -152,7 +152,7 @@ theorem sum_subgroup_units_eq_zero [Ring K] [NoZeroDivisors K]
   have h_sum_map := Finset.univ.sum_map a_mul_emb fun x => ((x : Kˣ) : K)
   -- ... and the former is the sum of x over G.
   -- By algebraic manipulation, we have Σ G, x = ∑ G, a x = a ∑ G, x
-  simp only [h_unchanged, Function.Embedding.coeFn_mk, Function.Embedding.toFun_eq_coe,
+  simp only [a_mul_emb, h_unchanged, Function.Embedding.coeFn_mk, Function.Embedding.toFun_eq_coe,
     mulLeftEmbedding_apply, Submonoid.coe_mul, Subgroup.coe_toSubmonoid, Units.val_mul,
     ← Finset.mul_sum] at h_sum_map
   -- thus one of (a - 1) or ∑ G, x is zero
@@ -298,7 +298,7 @@ theorem sum_pow_units [DecidableEq K] (i : ℕ) :
               cast_card_eq_zero, Nat.cast_one, zero_sub]
             show 1 ≤ q; exact Fintype.card_pos_iff.mpr ⟨0⟩
         rw [← forall_pow_eq_one_iff, DFunLike.ext_iff]
-        apply forall_congr'; intro x; simp [Units.ext_iff]
+        apply forall_congr'; intro x; simp [φ, Units.ext_iff]
 #align finite_field.sum_pow_units FiniteField.sum_pow_units
 
 /-- The sum of `x ^ i` as `x` ranges over a finite field of cardinality `q`
@@ -311,12 +311,12 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0
     let φ : Kˣ ↪ K := ⟨fun x ↦ x, Units.ext⟩
     have : univ.map φ = univ \ {0} := by
       ext x
-      simp only [true_and_iff, Function.Embedding.coeFn_mk, mem_sdiff, Units.exists_iff_ne_zero,
+      simp only [φ, true_and_iff, Function.Embedding.coeFn_mk, mem_sdiff, Units.exists_iff_ne_zero,
         mem_univ, mem_map, exists_prop_of_true, mem_singleton]
     calc
       ∑ x : K, x ^ i = ∑ x in univ \ {(0 : K)}, x ^ i := by
         rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton, zero_pow hi, add_zero]
-      _ = ∑ x : Kˣ, (x ^ i : K) := by simp [← this, univ.sum_map φ]
+      _ = ∑ x : Kˣ, (x ^ i : K) := by simp [φ, ← this, univ.sum_map φ]
       _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 
@@ -416,7 +416,7 @@ theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p,
       (by rw [ZMod.card, hp_odd])
   refine' ⟨a, b, _⟩
   rw [← sub_eq_zero]
-  simpa only [eval_C, eval_X, eval_pow, eval_sub, ← add_sub_assoc] using hab
+  simpa only [f, g, eval_C, eval_X, eval_pow, eval_sub, ← add_sub_assoc] using hab
 #align zmod.sq_add_sq ZMod.sq_add_sq
 
 end ZMod
chore: remove stream-of-consciousness uses of have, replace and suffices (#10640)

No changes to tactic file, it's just boring fixes throughout the library.

This follows on from #6964.

Co-authored-by: sgouezel <sebastien.gouezel@univ-rennes1.fr> Co-authored-by: Eric Wieser <wieser.eric@gmail.com>

Diff
@@ -196,10 +196,9 @@ theorem sum_subgroup_pow_eq_zero [CommRing K] [NoZeroDivisors K]
     congr
     rw [eq_comm]
     exact Multiset.map_univ_val_equiv (Equiv.mulRight a)
-  have h_multiset_map_sum :
-    (Multiset.map (fun x : G => ((x : Kˣ) : K) ^ k) Finset.univ.val).sum =
-      (Multiset.map (fun x : G => ((x : Kˣ) : K) ^ k * ((a : Kˣ) : K) ^ k) Finset.univ.val).sum
-  rw [h_multiset_map]
+  have h_multiset_map_sum : (Multiset.map (fun x : G => ((x : Kˣ) : K) ^ k) Finset.univ.val).sum =
+    (Multiset.map (fun x : G => ((x : Kˣ) : K) ^ k * ((a : Kˣ) : K) ^ k) Finset.univ.val).sum := by
+    rw [h_multiset_map]
   rw [Multiset.sum_map_mul_right] at h_multiset_map_sum
   have hzero : (((a : Kˣ) : K) ^ k - 1 : K)
                   * (Multiset.map (fun i : G => (i.val : K) ^ k) Finset.univ.val).sum = 0 := by
feat: (s ∩ t).card = s.card + t.card - (s ∪ t).card (#10224)

once coerced to an AddGroupWithOne. Also unify Finset.card_disjoint_union and Finset.card_union_eq

From LeanAPAP

Diff
@@ -95,7 +95,7 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
             (mt (congr_arg (· % 2)) (by simp [natDegree_eq_of_degree_eq_some hf2, hR])))
           (card_image_polynomial_eval (by rw [degree_neg, hg2]; exact by decide)))
       _ = 2 * ((univ.image fun x : R => eval x f) ∪ univ.image fun x : R => eval x (-g)).card := by
-        rw [card_disjoint_union hd];
+        rw [card_union_of_disjoint hd];
           simp [natDegree_eq_of_degree_eq_some hf2, natDegree_eq_of_degree_eq_some hg2, mul_add]
 
 #align finite_field.exists_root_sum_quadratic FiniteField.exists_root_sum_quadratic
feat: The support of f ^ n (#9617)

This involves moving lemmas from Algebra.GroupPower.Ring to Algebra.GroupWithZero.Basic and changing some 0 < n assumptions to n ≠ 0.

From LeanAPAP

Diff
@@ -228,10 +228,9 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 := by
 #align finite_field.pow_card_sub_one_eq_one FiniteField.pow_card_sub_one_eq_one
 
 theorem pow_card (a : K) : a ^ q = a := by
-  have hp : 0 < Fintype.card K := lt_trans zero_lt_one Fintype.one_lt_card
-  by_cases h : a = 0; · rw [h]; apply zero_pow hp
-  rw [← Nat.succ_pred_eq_of_pos hp, pow_succ, Nat.pred_eq_sub_one, pow_card_sub_one_eq_one a h,
-    mul_one]
+  by_cases h : a = 0; · rw [h]; apply zero_pow Fintype.card_ne_zero
+  rw [← Nat.succ_pred_eq_of_pos Fintype.card_pos, pow_succ, Nat.pred_eq_sub_one,
+    pow_card_sub_one_eq_one a h, mul_one]
 #align finite_field.pow_card FiniteField.pow_card
 
 theorem pow_card_pow (n : ℕ) (a : K) : a ^ q ^ n = a := by
@@ -317,8 +316,7 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0
         mem_univ, mem_map, exists_prop_of_true, mem_singleton]
     calc
       ∑ x : K, x ^ i = ∑ x in univ \ {(0 : K)}, x ^ i := by
-        rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton,
-          zero_pow (Nat.pos_of_ne_zero hi), add_zero]
+        rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton, zero_pow hi, add_zero]
       _ = ∑ x : Kˣ, (x ^ i : K) := by simp [← this, univ.sum_map φ]
       _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
chore(FieldTheory/Finite): golf (#9931)

Motivated by @Ruben-VandeVelde's leanprover-community/mathlib#15206

Diff
@@ -586,17 +586,9 @@ theorem isSquare_of_char_two (hF : ringChar F = 2) (a : F) : IsSquare a :=
 /-- In a finite field of odd characteristic, not every element is a square. -/
 theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a := by
   -- Idea: the squaring map on `F` is not injective, hence not surjective
-  let sq : F → F := fun x => x ^ 2
-  have h : ¬Function.Injective sq := by
-    simp only [Function.Injective, not_forall, exists_prop]
-    refine' ⟨-1, 1, _, Ring.neg_one_ne_one_of_char_ne_two hF⟩
-    simp only [one_pow, neg_one_sq]
-  rw [Finite.injective_iff_surjective] at h
-  -- sq not surjective
-  simp_rw [IsSquare, ← pow_two, @eq_comm _ _ (_ ^ 2)]
-  unfold Function.Surjective at h
-  push_neg at h ⊢
-  exact h
+  have h : ¬Function.Injective fun x : F ↦ x * x := fun h ↦
+    h.ne (Ring.neg_one_ne_one_of_char_ne_two hF) <| by simp
+  simpa [Finite.injective_iff_surjective, Function.Surjective, IsSquare, eq_comm] using h
 #align finite_field.exists_nonsquare FiniteField.exists_nonsquare
 
 end Finite
@@ -606,14 +598,8 @@ variable [Fintype F]
 /-- The finite field `F` has even cardinality iff it has characteristic `2`. -/
 theorem even_card_iff_char_two : ringChar F = 2 ↔ Fintype.card F % 2 = 0 := by
   rcases FiniteField.card F (ringChar F) with ⟨n, hp, h⟩
-  rw [h, Nat.pow_mod]
-  constructor
-  · intro hF
-    simp [hF]
-  · rw [← Nat.even_iff, Nat.even_pow]
-    rintro ⟨hev, hnz⟩
-    rw [Nat.even_iff, Nat.mod_mod] at hev
-    exact (Nat.Prime.eq_two_or_odd hp).resolve_right (ne_of_eq_of_ne hev zero_ne_one)
+  rw [h, ← Nat.even_iff, Nat.even_pow, hp.even_iff]
+  simp
 #align finite_field.even_card_iff_char_two FiniteField.even_card_iff_char_two
 
 theorem even_card_of_char_two (hF : ringChar F = 2) : Fintype.card F % 2 = 0 :=
chore(*): rename FunLike to DFunLike (#9785)

This prepares for the introduction of a non-dependent synonym of FunLike, which helps a lot with keeping #8386 readable.

This is entirely search-and-replace in 680197f combined with manual fixes in 4145626, e900597 and b8428f8. The commands that generated this change:

sed -i 's/\bFunLike\b/DFunLike/g' {Archive,Counterexamples,Mathlib,test}/**/*.lean
sed -i 's/\btoFunLike\b/toDFunLike/g' {Archive,Counterexamples,Mathlib,test}/**/*.lean
sed -i 's/import Mathlib.Data.DFunLike/import Mathlib.Data.FunLike/g' {Archive,Counterexamples,Mathlib,test}/**/*.lean
sed -i 's/\bHom_FunLike\b/Hom_DFunLike/g' {Archive,Counterexamples,Mathlib,test}/**/*.lean     
sed -i 's/\binstFunLike\b/instDFunLike/g' {Archive,Counterexamples,Mathlib,test}/**/*.lean
sed -i 's/\bfunLike\b/instDFunLike/g' {Archive,Counterexamples,Mathlib,test}/**/*.lean
sed -i 's/\btoo many metavariables to apply `fun_like.has_coe_to_fun`/too many metavariables to apply `DFunLike.hasCoeToFun`/g' {Archive,Counterexamples,Mathlib,test}/**/*.lean

Co-authored-by: Anne Baanen <Vierkantor@users.noreply.github.com>

Diff
@@ -299,7 +299,7 @@ theorem sum_pow_units [DecidableEq K] (i : ℕ) :
           · rw [Fintype.card_units, Nat.cast_sub,
               cast_card_eq_zero, Nat.cast_one, zero_sub]
             show 1 ≤ q; exact Fintype.card_pos_iff.mpr ⟨0⟩
-        rw [← forall_pow_eq_one_iff, FunLike.ext_iff]
+        rw [← forall_pow_eq_one_iff, DFunLike.ext_iff]
         apply forall_congr'; intro x; simp [Units.ext_iff]
 #align finite_field.sum_pow_units FiniteField.sum_pow_units
 
chore: Rename pow monotonicity lemmas (#9095)

The names for lemmas about monotonicity of (a ^ ·) and (· ^ n) were a mess. This PR tidies up everything related by following the naming convention for (a * ·) and (· * b). Namely, (a ^ ·) is pow_right and (· ^ n) is pow_left in lemma names. All lemma renames follow the corresponding multiplication lemma names closely.

Renames

Algebra.GroupPower.Order

  • pow_monopow_right_mono
  • pow_le_powpow_le_pow_right
  • pow_le_pow_of_le_leftpow_le_pow_left
  • pow_lt_pow_of_lt_leftpow_lt_pow_left
  • strictMonoOn_powpow_left_strictMonoOn
  • pow_strictMono_rightpow_right_strictMono
  • pow_lt_powpow_lt_pow_right
  • pow_lt_pow_iffpow_lt_pow_iff_right
  • pow_le_pow_iffpow_le_pow_iff_right
  • self_lt_powlt_self_pow
  • strictAnti_powpow_right_strictAnti
  • pow_lt_pow_iff_of_lt_onepow_lt_pow_iff_right_of_lt_one
  • pow_lt_pow_of_lt_onepow_lt_pow_right_of_lt_one
  • lt_of_pow_lt_powlt_of_pow_lt_pow_left
  • le_of_pow_le_powle_of_pow_le_pow_left
  • pow_lt_pow₀pow_lt_pow_right₀

Algebra.GroupPower.CovariantClass

  • pow_le_pow_of_le_left'pow_le_pow_left'
  • nsmul_le_nsmul_of_le_rightnsmul_le_nsmul_right
  • pow_lt_pow'pow_lt_pow_right'
  • nsmul_lt_nsmulnsmul_lt_nsmul_left
  • pow_strictMono_leftpow_right_strictMono'
  • nsmul_strictMono_rightnsmul_left_strictMono
  • StrictMono.pow_right'StrictMono.pow_const
  • StrictMono.nsmul_leftStrictMono.const_nsmul
  • pow_strictMono_right'pow_left_strictMono
  • nsmul_strictMono_leftnsmul_right_strictMono
  • Monotone.pow_rightMonotone.pow_const
  • Monotone.nsmul_leftMonotone.const_nsmul
  • lt_of_pow_lt_pow'lt_of_pow_lt_pow_left'
  • lt_of_nsmul_lt_nsmullt_of_nsmul_lt_nsmul_right
  • pow_le_pow'pow_le_pow_right'
  • nsmul_le_nsmulnsmul_le_nsmul_left
  • pow_le_pow_of_le_one'pow_le_pow_right_of_le_one'
  • nsmul_le_nsmul_of_nonposnsmul_le_nsmul_left_of_nonpos
  • le_of_pow_le_pow'le_of_pow_le_pow_left'
  • le_of_nsmul_le_nsmul'le_of_nsmul_le_nsmul_right'
  • pow_le_pow_iff'pow_le_pow_iff_right'
  • nsmul_le_nsmul_iffnsmul_le_nsmul_iff_left
  • pow_lt_pow_iff'pow_lt_pow_iff_right'
  • nsmul_lt_nsmul_iffnsmul_lt_nsmul_iff_left

Data.Nat.Pow

  • Nat.pow_lt_pow_of_lt_leftNat.pow_lt_pow_left
  • Nat.pow_le_iff_le_leftNat.pow_le_pow_iff_left
  • Nat.pow_lt_iff_lt_leftNat.pow_lt_pow_iff_left

Lemmas added

  • pow_le_pow_iff_left
  • pow_lt_pow_iff_left
  • pow_right_injective
  • pow_right_inj
  • Nat.pow_le_pow_left to have the correct name since Nat.pow_le_pow_of_le_left is in Std.
  • Nat.pow_le_pow_right to have the correct name since Nat.pow_le_pow_of_le_right is in Std.

Lemmas removed

  • self_le_pow was a duplicate of le_self_pow.
  • Nat.pow_lt_pow_of_lt_right is defeq to pow_lt_pow_right.
  • Nat.pow_right_strictMono is defeq to pow_right_strictMono.
  • Nat.pow_le_iff_le_right is defeq to pow_le_pow_iff_right.
  • Nat.pow_lt_iff_lt_right is defeq to pow_lt_pow_iff_right.

Other changes

  • A bunch of proofs have been golfed.
  • Some lemma assumptions have been turned from 0 < n or 1 ≤ n to n ≠ 0.
  • A few Nat lemmas have been protected.
  • One docstring has been fixed.
Diff
@@ -339,7 +339,7 @@ set_option linter.uppercaseLean3 false in
 
 theorem X_pow_card_pow_sub_X_natDegree_eq (hn : n ≠ 0) (hp : 1 < p) :
     (X ^ p ^ n - X : K'[X]).natDegree = p ^ n :=
-  X_pow_card_sub_X_natDegree_eq K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
+  X_pow_card_sub_X_natDegree_eq K' <| Nat.one_lt_pow _ _ hn hp
 set_option linter.uppercaseLean3 false in
 #align finite_field.X_pow_card_pow_sub_X_nat_degree_eq FiniteField.X_pow_card_pow_sub_X_natDegree_eq
 
@@ -352,7 +352,7 @@ set_option linter.uppercaseLean3 false in
 #align finite_field.X_pow_card_sub_X_ne_zero FiniteField.X_pow_card_sub_X_ne_zero
 
 theorem X_pow_card_pow_sub_X_ne_zero (hn : n ≠ 0) (hp : 1 < p) : (X ^ p ^ n - X : K'[X]) ≠ 0 :=
-  X_pow_card_sub_X_ne_zero K' <| Nat.one_lt_pow _ _ (Nat.pos_of_ne_zero hn) hp
+  X_pow_card_sub_X_ne_zero K' <| Nat.one_lt_pow _ _ hn hp
 set_option linter.uppercaseLean3 false in
 #align finite_field.X_pow_card_pow_sub_X_ne_zero FiniteField.X_pow_card_pow_sub_X_ne_zero
 
chore: split Algebra.CharP.Basic, reduce imports in RingTheory.Multiplicity (#8637)

This was adding unnecessary imports to Data.ZMod.Basic.

Co-authored-by: Scott Morrison <scott.morrison@gmail.com>

Diff
@@ -5,6 +5,7 @@ Authors: Chris Hughes, Joey van Langen, Casper Putz
 -/
 import Mathlib.FieldTheory.Separable
 import Mathlib.RingTheory.IntegralDomain
+import Mathlib.Algebra.CharP.Reduced
 import Mathlib.Tactic.ApplyFun
 
 #align_import field_theory.finite.basic from "leanprover-community/mathlib"@"12a85fac627bea918960da036049d611b1a3ee43"
chore: space after (#8178)

Co-authored-by: Moritz Firsching <firsching@google.com>

Diff
@@ -156,11 +156,11 @@ theorem sum_subgroup_units_eq_zero [Ring K] [NoZeroDivisors K]
     ← Finset.mul_sum] at h_sum_map
   -- thus one of (a - 1) or ∑ G, x is zero
   have hzero : (((a : Kˣ) : K) - 1) = 0 ∨ ∑ x : ↥G, ((x : Kˣ) : K) = 0 := by
-    rw [←mul_eq_zero, sub_mul, ← h_sum_map, one_mul, sub_self]
+    rw [← mul_eq_zero, sub_mul, ← h_sum_map, one_mul, sub_self]
   apply Or.resolve_left hzero
   contrapose! ha
   ext
-  rwa [←sub_eq_zero]
+  rwa [← sub_eq_zero]
 
 /-- The sum of a subgroup of the units of a field is 1 if the subgroup is trivial and 1 otherwise -/
 @[simp]
@@ -207,7 +207,7 @@ theorem sum_subgroup_pow_eq_zero [CommRing K] [NoZeroDivisors K]
   rcases hzero with h | h
   · contrapose! ha
     ext
-    rw [←sub_eq_zero]
+    rw [← sub_eq_zero]
     simp_rw [SubmonoidClass.coe_pow, Units.val_pow_eq_pow_val, OneMemClass.coe_one,
       Units.val_one, h]
   · exact h
feat: bounds for Dirichlet characters (#8449)

This adds NumberTheory.DirichletCharacter.Bounds containing proofs of ‖χ a‖ = 1 if a is a unit and ‖χ a‖ ≤ 1 in general, where χ is a Dirichlet character with values in a normed field.

There are also two API lemmas added elsewhere that are used in the proofs.

Diff
@@ -479,6 +479,11 @@ theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.Coprime x n) : x ^ φ n ≡ 1
     coe_unitOfCoprime, Units.val_pow_eq_pow_val]
 #align nat.modeq.pow_totient Nat.ModEq.pow_totient
 
+/-- For each `n ≥ 0`, the unit group of `ZMod n` is finite. -/
+instance instFiniteZModUnits : (n : ℕ) → Finite (ZMod n)ˣ
+| 0     => Finite.of_fintype ℤˣ
+| _ + 1 => instFiniteUnits
+
 section
 
 variable {V : Type*} [Fintype K] [DivisionRing K] [AddCommGroup V] [Module K V]
chore: replace exact_mod_cast tactic with mod_cast elaborator where possible (#8404)

We still have the exact_mod_cast tactic, used in a few places, which somehow (?) works a little bit harder to prevent the expected type influencing the elaboration of the term. I would like to get to the bottom of this, and it will be easier once the only usages of exact_mod_cast are the ones that don't work using the term elaborator by itself.

Co-authored-by: Scott Morrison <scott.morrison@gmail.com>

Diff
@@ -331,8 +331,7 @@ variable (K' : Type*) [Field K'] {p n : ℕ}
 theorem X_pow_card_sub_X_natDegree_eq (hp : 1 < p) : (X ^ p - X : K'[X]).natDegree = p := by
   have h1 : (X : K'[X]).degree < (X ^ p : K'[X]).degree := by
     rw [degree_X_pow, degree_X]
-    -- Porting note: the following line was `exact_mod_cast hp`
-    exact WithBot.coe_lt_coe.2 hp
+    exact mod_cast hp
   rw [natDegree_eq_of_degree_eq (degree_sub_eq_left_of_degree_lt h1), natDegree_X_pow]
 set_option linter.uppercaseLean3 false in
 #align finite_field.X_pow_card_sub_X_nat_degree_eq FiniteField.X_pow_card_sub_X_natDegree_eq
@@ -435,7 +434,7 @@ theorem Nat.sq_add_sq_zmodEq (p : ℕ) [Fact p.Prime] (x : ℤ) :
   rw [← a.coe_valMinAbs, ← b.coe_valMinAbs] at hx
   push_cast
   rw [sq_abs, sq_abs, ← ZMod.int_cast_eq_int_cast_iff]
-  exact_mod_cast hx
+  exact mod_cast hx
 
 /-- If `p` is a prime natural number and `x` is a natural number, then there exist natural numbers
 `a ≤ p / 2` and `b ≤ p / 2` such that `a ^ 2 + b ^ 2 ≡ x [MOD p]`. This is a version of
feat: Order of elements of a subgroup (#8385)

The cardinality of a subgroup is greater than the order of any of its elements.

Rename

  • order_eq_card_zpowersFintype.card_zpowers
  • order_eq_card_zpowers'Nat.card_zpowers (and turn it around to match Nat.card_subgroupPowers)
  • Submonoid.powers_subsetSubmonoid.powers_le
  • orderOf_dvd_card_univorderOf_dvd_card
  • orderOf_subgroupSubgroup.orderOf
  • Subgroup.nonemptySubgroup.coe_nonempty
Diff
@@ -126,7 +126,7 @@ theorem card_cast_subgroup_card_ne_zero [Ring K] [NoZeroDivisors K] [Nontrivial
     have ⟨x, hx⟩ := exists_prime_orderOf_dvd_card p hd
     -- F has an element u (= ↑↑x) of order p
     let u := ((x : Kˣ) : K)
-    have hu : orderOf u = p := by rwa [orderOf_units, orderOf_subgroup]
+    have hu : orderOf u = p := by rwa [orderOf_units, Subgroup.orderOf_coe]
     -- u ^ p = 1 implies (u - 1) ^ p = 0 and hence u = 1 ...
     have h : u = 1 := by
       rw [← sub_left_inj, sub_self 1]
feat: add theorem cast_subgroup_of_units_card_ne_zero (#6500)

Adds a theorem saying the cardinality of a multiplicative subgroup of a field, cast to the field, is nonzero. As well as sum_subgroup_units_zero_of_ne_bot and other theorems about summing over multiplicative subgroups.

Co-authored-by: Pratyush Mishra <prat@upenn.edu> Co-authored-by: Buster <rcopley@gmail.com>

Diff
@@ -111,6 +111,107 @@ theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
     rw [← insert_erase (mem_univ (-1 : Kˣ)), prod_insert (not_mem_erase _ _), this, mul_one]
 #align finite_field.prod_univ_units_id_eq_neg_one FiniteField.prod_univ_units_id_eq_neg_one
 
+theorem card_cast_subgroup_card_ne_zero [Ring K] [NoZeroDivisors K] [Nontrivial K]
+    (G : Subgroup Kˣ) [Fintype G] : (Fintype.card G : K) ≠ 0 := by
+  let n := Fintype.card G
+  intro nzero
+  have ⟨p, char_p⟩ := CharP.exists K
+  have hd : p ∣ n := (CharP.cast_eq_zero_iff K p n).mp nzero
+  cases CharP.char_is_prime_or_zero K p with
+  | inr pzero =>
+    exact (Fintype.card_pos).ne' <| Nat.eq_zero_of_zero_dvd <| pzero ▸ hd
+  | inl pprime =>
+    have fact_pprime := Fact.mk pprime
+    -- G has an element x of order p by Cauchy's theorem
+    have ⟨x, hx⟩ := exists_prime_orderOf_dvd_card p hd
+    -- F has an element u (= ↑↑x) of order p
+    let u := ((x : Kˣ) : K)
+    have hu : orderOf u = p := by rwa [orderOf_units, orderOf_subgroup]
+    -- u ^ p = 1 implies (u - 1) ^ p = 0 and hence u = 1 ...
+    have h : u = 1 := by
+      rw [← sub_left_inj, sub_self 1]
+      apply pow_eq_zero (n := p)
+      rw [sub_pow_char_of_commute, one_pow, ← hu, pow_orderOf_eq_one, sub_self]
+      exact Commute.one_right u
+    -- ... meaning x didn't have order p after all, contradiction
+    apply pprime.one_lt.ne
+    rw [← hu, h, orderOf_one]
+
+/-- The sum of a nontrivial subgroup of the units of a field is zero. -/
+theorem sum_subgroup_units_eq_zero [Ring K] [NoZeroDivisors K]
+    {G : Subgroup Kˣ} [Fintype G] (hg : G ≠ ⊥) :
+    ∑ x : G, (x.val : K) = 0 := by
+  rw [Subgroup.ne_bot_iff_exists_ne_one] at hg
+  rcases hg with ⟨a, ha⟩
+  -- The action of a on G as an embedding
+  let a_mul_emb : G ↪ G := mulLeftEmbedding a
+  -- ... and leaves G unchanged
+  have h_unchanged : Finset.univ.map a_mul_emb = Finset.univ := by simp
+  -- Therefore the sum of x over a G is the sum of a x over G
+  have h_sum_map := Finset.univ.sum_map a_mul_emb fun x => ((x : Kˣ) : K)
+  -- ... and the former is the sum of x over G.
+  -- By algebraic manipulation, we have Σ G, x = ∑ G, a x = a ∑ G, x
+  simp only [h_unchanged, Function.Embedding.coeFn_mk, Function.Embedding.toFun_eq_coe,
+    mulLeftEmbedding_apply, Submonoid.coe_mul, Subgroup.coe_toSubmonoid, Units.val_mul,
+    ← Finset.mul_sum] at h_sum_map
+  -- thus one of (a - 1) or ∑ G, x is zero
+  have hzero : (((a : Kˣ) : K) - 1) = 0 ∨ ∑ x : ↥G, ((x : Kˣ) : K) = 0 := by
+    rw [←mul_eq_zero, sub_mul, ← h_sum_map, one_mul, sub_self]
+  apply Or.resolve_left hzero
+  contrapose! ha
+  ext
+  rwa [←sub_eq_zero]
+
+/-- The sum of a subgroup of the units of a field is 1 if the subgroup is trivial and 1 otherwise -/
+@[simp]
+theorem sum_subgroup_units [Ring K] [NoZeroDivisors K]
+    {G : Subgroup Kˣ} [Fintype G] [Decidable (G = ⊥)] :
+    ∑ x : G, (x.val : K) = if G = ⊥ then 1 else 0 := by
+  by_cases G_bot : G = ⊥
+  · subst G_bot
+    simp only [ite_true, Subgroup.mem_bot, Fintype.card_ofSubsingleton, Nat.cast_ite, Nat.cast_one,
+      Nat.cast_zero, univ_unique, Set.default_coe_singleton, sum_singleton, Units.val_one]
+  · simp only [G_bot, ite_false]
+    exact sum_subgroup_units_eq_zero G_bot
+
+@[simp]
+theorem sum_subgroup_pow_eq_zero [CommRing K] [NoZeroDivisors K]
+    {G : Subgroup Kˣ} [Fintype G] {k : ℕ} (k_pos : k ≠ 0) (k_lt_card_G : k < Fintype.card G) :
+    ∑ x : G, ((x : Kˣ) : K) ^ k = 0 := by
+  nontriviality K
+  have := NoZeroDivisors.to_isDomain K
+  rcases (exists_pow_ne_one_of_isCyclic k_pos k_lt_card_G) with ⟨a, ha⟩
+  rw [Finset.sum_eq_multiset_sum]
+  have h_multiset_map :
+    Finset.univ.val.map (fun x : G => ((x : Kˣ) : K) ^ k) =
+      Finset.univ.val.map (fun x : G => ((x : Kˣ) : K) ^ k * ((a : Kˣ) : K) ^ k) := by
+    simp_rw [← mul_pow]
+    have as_comp :
+      (fun x : ↥G => (((x : Kˣ) : K) * ((a : Kˣ) : K)) ^ k)
+        = (fun x : ↥G => ((x : Kˣ) : K) ^ k) ∘ fun x : ↥G => x * a := by
+      funext x
+      simp only [Function.comp_apply, Submonoid.coe_mul, Subgroup.coe_toSubmonoid, Units.val_mul]
+    rw [as_comp, ← Multiset.map_map]
+    congr
+    rw [eq_comm]
+    exact Multiset.map_univ_val_equiv (Equiv.mulRight a)
+  have h_multiset_map_sum :
+    (Multiset.map (fun x : G => ((x : Kˣ) : K) ^ k) Finset.univ.val).sum =
+      (Multiset.map (fun x : G => ((x : Kˣ) : K) ^ k * ((a : Kˣ) : K) ^ k) Finset.univ.val).sum
+  rw [h_multiset_map]
+  rw [Multiset.sum_map_mul_right] at h_multiset_map_sum
+  have hzero : (((a : Kˣ) : K) ^ k - 1 : K)
+                  * (Multiset.map (fun i : G => (i.val : K) ^ k) Finset.univ.val).sum = 0 := by
+    rw [sub_mul, mul_comm, ← h_multiset_map_sum, one_mul, sub_self]
+  rw [mul_eq_zero] at hzero
+  rcases hzero with h | h
+  · contrapose! ha
+    ext
+    rw [←sub_eq_zero]
+    simp_rw [SubmonoidClass.coe_pow, Units.val_pow_eq_pow_val, OneMemClass.coe_one,
+      Units.val_one, h]
+  · exact h
+
 section
 
 variable [GroupWithZero K] [Fintype K]
chore: bump to v4.1.0-rc1 (2nd attempt) (#7216)

Co-authored-by: Eric Wieser <wieser.eric@gmail.com> Co-authored-by: Scott Morrison <scott.morrison@gmail.com>

Diff
@@ -370,7 +370,7 @@ theorem ZMod.pow_totient {n : ℕ} (x : (ZMod n)ˣ) : x ^ φ n = 1 := by
 
 /-- The **Fermat-Euler totient theorem**. `ZMod.pow_totient` is an alternative statement
   of the same theorem. -/
-theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1 [MOD n] := by
+theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.Coprime x n) : x ^ φ n ≡ 1 [MOD n] := by
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
   have := ZMod.pow_totient x'
Revert "chore: bump to v4.1.0-rc1 (#7174)" (#7198)

This reverts commit 6f8e8104. Unfortunately this bump was not linted correctly, as CI did not run runLinter Mathlib.

We can unrevert once that's fixed.

Diff
@@ -370,7 +370,7 @@ theorem ZMod.pow_totient {n : ℕ} (x : (ZMod n)ˣ) : x ^ φ n = 1 := by
 
 /-- The **Fermat-Euler totient theorem**. `ZMod.pow_totient` is an alternative statement
   of the same theorem. -/
-theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.Coprime x n) : x ^ φ n ≡ 1 [MOD n] := by
+theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1 [MOD n] := by
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
   have := ZMod.pow_totient x'
chore: bump to v4.1.0-rc1 (#7174)

Some changes have already been review and delegated in #6910 and #7148.

The diff that needs looking at is https://github.com/leanprover-community/mathlib4/pull/7174/commits/64d6d07ee18163627c8f517eb31455411921c5ac

The std bump PR was insta-merged already!

Co-authored-by: leanprover-community-mathlib4-bot <leanprover-community-mathlib4-bot@users.noreply.github.com> Co-authored-by: Scott Morrison <scott.morrison@gmail.com>

Diff
@@ -370,7 +370,7 @@ theorem ZMod.pow_totient {n : ℕ} (x : (ZMod n)ˣ) : x ^ φ n = 1 := by
 
 /-- The **Fermat-Euler totient theorem**. `ZMod.pow_totient` is an alternative statement
   of the same theorem. -/
-theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1 [MOD n] := by
+theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.Coprime x n) : x ^ φ n ≡ 1 [MOD n] := by
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
   have := ZMod.pow_totient x'
feat: use the function to help elaborate the injectivity lemma in apply_fun (#6733)

Co-authored-by: Kyle Miller <kmill31415@gmail.com>

Diff
@@ -538,7 +538,7 @@ theorem unit_isSquare_iff (hF : ringChar F ≠ 2) (a : Fˣ) :
     constructor
     · rintro ⟨y, rfl⟩
       rw [← pow_two, ← pow_mul, hodd]
-      apply_fun Units.val using Units.ext (α := F)
+      apply_fun Units.val using Units.ext
       · push_cast
         exact FiniteField.pow_card_sub_one_eq_one (y : F) (Units.ne_zero y)
     · subst a; intro h
chore: drop MulZeroClass. in mul_zero/zero_mul (#6682)

Search&replace MulZeroClass.mul_zero -> mul_zero, MulZeroClass.zero_mul -> zero_mul.

These were introduced by Mathport, as the full name of mul_zero is actually MulZeroClass.mul_zero (it's exported with the short name).

Diff
@@ -272,7 +272,7 @@ theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := b
     rw [separable_def]
     convert isCoprime_one_right.neg_right (R := K[X]) using 1
     rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
-      MulZeroClass.zero_mul, zero_sub]
+      zero_mul, zero_sub]
 set_option linter.uppercaseLean3 false in
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_X_pow_card_sub_X
 
chore: banish Type _ and Sort _ (#6499)

We remove all possible occurences of Type _ and Sort _ in favor of Type* and Sort*.

This has nice performance benefits.

Diff
@@ -43,7 +43,7 @@ diamonds, as `Fintype` carries data.
 -/
 
 
-variable {K : Type _} {R : Type _}
+variable {K : Type*} {R : Type*}
 
 -- mathport name: exprq
 local notation "q" => Fintype.card K
@@ -225,7 +225,7 @@ open Polynomial
 
 section
 
-variable (K' : Type _) [Field K'] {p n : ℕ}
+variable (K' : Type*) [Field K'] {p n : ℕ}
 
 theorem X_pow_card_sub_X_natDegree_eq (hp : 1 < p) : (X ^ p - X : K'[X]).natDegree = p := by
   have h1 : (X : K'[X]).degree < (X ^ p : K'[X]).degree := by
@@ -345,7 +345,7 @@ theorem Nat.sq_add_sq_modEq (p : ℕ) [Fact p.Prime] (x : ℕ) :
 
 namespace CharP
 
-theorem sq_add_sq (R : Type _) [CommRing R] [IsDomain R] (p : ℕ) [NeZero p] [CharP R p] (x : ℤ) :
+theorem sq_add_sq (R : Type*) [CommRing R] [IsDomain R] (p : ℕ) [NeZero p] [CharP R p] (x : ℤ) :
     ∃ a b : ℕ, ((a : R) ^ 2 + (b : R) ^ 2) = x := by
   haveI := char_is_prime_of_pos R p
   obtain ⟨a, b, hab⟩ := ZMod.sq_add_sq p x
@@ -381,7 +381,7 @@ theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1
 
 section
 
-variable {V : Type _} [Fintype K] [DivisionRing K] [AddCommGroup V] [Module K V]
+variable {V : Type*} [Fintype K] [DivisionRing K] [AddCommGroup V] [Module K V]
 
 -- should this go in a namespace?
 -- finite_dimensional would be natural,
@@ -465,7 +465,7 @@ section
 
 namespace FiniteField
 
-variable {F : Type _} [Field F]
+variable {F : Type*} [Field F]
 
 section Finite
 
chore: fix grammar mistakes (#6121)
Diff
@@ -22,7 +22,7 @@ cyclic group, as well as the fact that every finite integral domain is a field
 
 ## Main results
 
-1. `Fintype.card_units`: The unit group of a finite field is has cardinality `q - 1`.
+1. `Fintype.card_units`: The unit group of a finite field has cardinality `q - 1`.
 2. `sum_pow_units`: The sum of `x^i`, where `x` ranges over the units of `K`, is
    - `q-1` if `q-1 ∣ i`
    - `0`   otherwise
feat: add card_units_add_one lemma (#5738)

A lemma to reexpress card_units without subtraction.

Diff
@@ -181,7 +181,7 @@ theorem forall_pow_eq_one_iff (i : ℕ) : (∀ x : Kˣ, x ^ i = 1) ↔ q - 1 ∣
 
 /-- The sum of `x ^ i` as `x` ranges over the units of a finite field of cardinality `q`
 is equal to `0` unless `(q - 1) ∣ i`, in which case the sum is `q - 1`. -/
-theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
+theorem sum_pow_units [DecidableEq K] (i : ℕ) :
     (∑ x : Kˣ, (x ^ i : K)) = if q - 1 ∣ i then -1 else 0 := by
   let φ : Kˣ →* K :=
     { toFun := fun x => x ^ i
chore: script to replace headers with #align_import statements (#5979)

Open in Gitpod

Co-authored-by: Eric Wieser <wieser.eric@gmail.com> Co-authored-by: Scott Morrison <scott.morrison@gmail.com>

Diff
@@ -2,16 +2,13 @@
 Copyright (c) 2018 Chris Hughes. All rights reserved.
 Released under Apache 2.0 license as described in the file LICENSE.
 Authors: Chris Hughes, Joey van Langen, Casper Putz
-
-! This file was ported from Lean 3 source module field_theory.finite.basic
-! leanprover-community/mathlib commit 12a85fac627bea918960da036049d611b1a3ee43
-! Please do not edit these lines, except to modify the commit id
-! if you have ported upstream changes.
 -/
 import Mathlib.FieldTheory.Separable
 import Mathlib.RingTheory.IntegralDomain
 import Mathlib.Tactic.ApplyFun
 
+#align_import field_theory.finite.basic from "leanprover-community/mathlib"@"12a85fac627bea918960da036049d611b1a3ee43"
+
 /-!
 # Finite fields
 
chore: remove occurrences of semicolon after space (#5713)

This is the second half of the changes originally in #5699, removing all occurrences of ; after a space and implementing a linter rule to enforce it.

In most cases this 2-character substring has a space after it, so the following command was run first:

find . -type f -name "*.lean" -exec sed -i -E 's/ ; /; /g' {} \;

The remaining cases were few enough in number that they were done manually.

Diff
@@ -189,7 +189,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
   let φ : Kˣ →* K :=
     { toFun := fun x => x ^ i
       map_one' := by simp
-      map_mul' := by intros ; simp [mul_pow] }
+      map_mul' := by intros; simp [mul_pow] }
   have : Decidable (φ = 1) := by classical infer_instance
   calc (∑ x : Kˣ, φ x) = if φ = 1 then Fintype.card Kˣ else 0 := sum_hom_units φ
       _ = if q - 1 ∣ i then -1 else 0 := by
fix: ∑' precedence (#5615)
  • Also remove most superfluous parentheses around big operators (, and variants).
  • roughly the used regex: ([^a-zA-Zα-ωΑ-Ω'𝓝ℳ₀𝕂ₛ)]) \(([∑∏][^()∑∏]*,[^()∑∏:]*)\) ([⊂⊆=<≤]) replaced by $1 $2 $3
Diff
@@ -105,7 +105,7 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
 end Polynomial
 
 theorem prod_univ_units_id_eq_neg_one [CommRing K] [IsDomain K] [Fintype Kˣ] :
-    (∏ x : Kˣ, x) = (-1 : Kˣ) := by
+    ∏ x : Kˣ, x = (-1 : Kˣ) := by
   classical
     have : (∏ x in (@univ Kˣ _).erase (-1), x) = 1 :=
       prod_involution (fun x _ => x⁻¹) (by simp)
@@ -206,7 +206,7 @@ theorem sum_pow_units [Fintype Kˣ] (i : ℕ) :
 
 /-- The sum of `x ^ i` as `x` ranges over a finite field of cardinality `q`
 is equal to `0` if `i < q - 1`. -/
-theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) = 0 := by
+theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : ∑ x : K, x ^ i = 0 := by
   by_cases hi : i = 0
   · simp only [hi, nsmul_one, sum_const, pow_zero, card_univ, cast_card_eq_zero]
   classical
@@ -217,7 +217,7 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
       simp only [true_and_iff, Function.Embedding.coeFn_mk, mem_sdiff, Units.exists_iff_ne_zero,
         mem_univ, mem_map, exists_prop_of_true, mem_singleton]
     calc
-      (∑ x : K, x ^ i) = ∑ x in univ \ {(0 : K)}, x ^ i := by
+      ∑ x : K, x ^ i = ∑ x in univ \ {(0 : K)}, x ^ i := by
         rw [← sum_sdiff ({0} : Finset K).subset_univ, sum_singleton,
           zero_pow (Nat.pos_of_ne_zero hi), add_zero]
       _ = ∑ x : Kˣ, (x ^ i : K) := by simp [← this, univ.sum_map φ]
chore: clean up spacing around at and goals (#5387)

Changes are of the form

  • some_tactic at h⊢ -> some_tactic at h ⊢
  • some_tactic at h -> some_tactic at h
Diff
@@ -82,7 +82,7 @@ theorem exists_root_sum_quadratic [Fintype R] {f g : R[X]} (hf2 : degree f = 2)
   suffices ¬Disjoint (univ.image fun x : R => eval x f)
     (univ.image fun x : R => eval x (-g)) by
     simp only [disjoint_left, mem_image] at this
-    push_neg  at this
+    push_neg at this
     rcases this with ⟨x, ⟨a, _, ha⟩, ⟨b, _, hb⟩⟩
     exact ⟨a, b, by rw [ha, ← hb, eval_neg, neg_add_self]⟩
   fun hd : Disjoint _ _ =>
@@ -377,7 +377,7 @@ theorem Nat.ModEq.pow_totient {x n : ℕ} (h : Nat.coprime x n) : x ^ φ n ≡ 1
   rw [← ZMod.eq_iff_modEq_nat]
   let x' : Units (ZMod n) := ZMod.unitOfCoprime _ h
   have := ZMod.pow_totient x'
-  apply_fun ((fun (x : Units (ZMod n)) => (x : ZMod n)) : Units (ZMod n) → ZMod n)  at this
+  apply_fun ((fun (x : Units (ZMod n)) => (x : ZMod n)) : Units (ZMod n) → ZMod n) at this
   simpa only [Nat.succ_eq_add_one, Nat.cast_pow, Units.val_one, Nat.cast_one,
     coe_unitOfCoprime, Units.val_pow_eq_pow_val]
 #align nat.modeq.pow_totient Nat.ModEq.pow_totient
@@ -492,7 +492,7 @@ theorem exists_nonsquare (hF : ringChar F ≠ 2) : ∃ a : F, ¬IsSquare a := by
   -- sq not surjective
   simp_rw [IsSquare, ← pow_two, @eq_comm _ _ (_ ^ 2)]
   unfold Function.Surjective at h
-  push_neg  at h⊢
+  push_neg at h ⊢
   exact h
 #align finite_field.exists_nonsquare FiniteField.exists_nonsquare
 
chore: formatting issues (#4947)

Co-authored-by: Scott Morrison <scott.morrison@anu.edu.au> Co-authored-by: Parcly Taxel <reddeloostw@gmail.com>

Diff
@@ -159,7 +159,7 @@ theorem card (p : ℕ) [CharP K p] : ∃ n : ℕ+, Nat.Prime p ∧ q = p ^ (n :
 #align finite_field.card FiniteField.card
 
 -- this statement doesn't use `q` because we want `K` to be an explicit parameter
-theorem card' : ∃ (p : ℕ)(n : ℕ+), Nat.Prime p ∧ Fintype.card K = p ^ (n : ℕ) :=
+theorem card' : ∃ (p : ℕ) (n : ℕ+), Nat.Prime p ∧ Fintype.card K = p ^ (n : ℕ) :=
   let ⟨p, hc⟩ := CharP.exists K
   ⟨p, @FiniteField.card K _ _ p hc⟩
 #align finite_field.card' FiniteField.card'
chore: tidy various files (#4757)
Diff
@@ -73,7 +73,6 @@ theorem card_image_polynomial_eval [DecidableEq R] [Fintype R] {p : R[X]} (hp :
         congr_arg card (by simp [Finset.ext_iff, ← mem_roots_sub_C hp])
       _ ≤ Multiset.card (p - C a).roots := (Multiset.toFinset_card_le _)
       _ ≤ _ := card_roots_sub_C' hp)
-
 #align finite_field.card_image_polynomial_eval FiniteField.card_image_polynomial_eval
 
 /-- If `f` and `g` are quadratic polynomials, then the `f.eval a + g.eval b = 0` has a solution. -/
@@ -127,7 +126,6 @@ theorem pow_card_sub_one_eq_one (a : K) (ha : a ≠ 0) : a ^ (q - 1) = 1 := by
       classical
         rw [← Fintype.card_units, pow_card_eq_one]
         rfl
-
 #align finite_field.pow_card_sub_one_eq_one FiniteField.pow_card_sub_one_eq_one
 
 theorem pow_card (a : K) : a ^ q = a := by
@@ -224,7 +222,6 @@ theorem sum_pow_lt_card_sub_one (i : ℕ) (h : i < q - 1) : (∑ x : K, x ^ i) =
           zero_pow (Nat.pos_of_ne_zero hi), add_zero]
       _ = ∑ x : Kˣ, (x ^ i : K) := by simp [← this, univ.sum_map φ]
       _ = 0 := by rw [sum_pow_units K i, if_neg]; exact hiq
-
 #align finite_field.sum_pow_lt_card_sub_one FiniteField.sum_pow_lt_card_sub_one
 
 open Polynomial
@@ -277,8 +274,8 @@ theorem roots_X_pow_card_sub_X : roots (X ^ q - X : K[X]) = Finset.univ.val := b
     apply nodup_roots
     rw [separable_def]
     convert isCoprime_one_right.neg_right (R := K[X]) using 1
-    · rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
-        MulZeroClass.zero_mul, zero_sub]
+    rw [derivative_sub, derivative_X, derivative_X_pow, CharP.cast_card_eq_zero K, C_0,
+      MulZeroClass.zero_mul, zero_sub]
 set_option linter.uppercaseLean3 false in
 #align finite_field.roots_X_pow_card_sub_X FiniteField.roots_X_pow_card_sub_X
 
@@ -315,7 +312,7 @@ theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p,
   · subst p
     change Fin 2 at x
     fin_cases x
-    · use 0; simp;
+    · use 0; simp
     · use 0, 1; simp
   let f : (ZMod p)[X] := X ^ 2
   let g : (ZMod p)[X] := X ^ 2 - C x
@@ -417,10 +414,10 @@ theorem pow_card_pow {n p : ℕ} [Fact p.Prime] (x : ZMod p) : x ^ p ^ n = x :=
 #align zmod.pow_card_pow ZMod.pow_card_pow
 
 @[simp]
-theorem frobenius_zMod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom.id _ := by
+theorem frobenius_zmod (p : ℕ) [Fact p.Prime] : frobenius (ZMod p) p = RingHom.id _ := by
   ext a
   rw [frobenius_def, ZMod.pow_card, RingHom.id_apply]
-#align zmod.frobenius_zmod ZMod.frobenius_zMod
+#align zmod.frobenius_zmod ZMod.frobenius_zmod
 
 --Porting note: this was a `simp` lemma, but now the LHS simplify to `φ p`.
 theorem card_units (p : ℕ) [Fact p.Prime] : Fintype.card (ZMod p)ˣ = p - 1 := by
feat: port NumberTheory.SumFourSquares (#4604)
Diff
@@ -329,6 +329,26 @@ theorem sq_add_sq (p : ℕ) [hp : Fact p.Prime] (x : ZMod p) : ∃ a b : ZMod p,
 
 end ZMod
 
+/-- If `p` is a prime natural number and `x` is an integer number, then there exist natural numbers
+`a ≤ p / 2` and `b ≤ p / 2` such that `a ^ 2 + b ^ 2 ≡ x [ZMOD p]`. This is a version of
+`ZMod.sq_add_sq` with estimates on `a` and `b`. -/
+theorem Nat.sq_add_sq_zmodEq (p : ℕ) [Fact p.Prime] (x : ℤ) :
+    ∃ a b : ℕ, a ≤ p / 2 ∧ b ≤ p / 2 ∧ (a : ℤ) ^ 2 + (b : ℤ) ^ 2 ≡ x [ZMOD p] := by
+  rcases ZMod.sq_add_sq p x with ⟨a, b, hx⟩
+  refine ⟨a.valMinAbs.natAbs, b.valMinAbs.natAbs, ZMod.natAbs_valMinAbs_le _,
+    ZMod.natAbs_valMinAbs_le _, ?_⟩
+  rw [← a.coe_valMinAbs, ← b.coe_valMinAbs] at hx
+  push_cast
+  rw [sq_abs, sq_abs, ← ZMod.int_cast_eq_int_cast_iff]
+  exact_mod_cast hx
+
+/-- If `p` is a prime natural number and `x` is a natural number, then there exist natural numbers
+`a ≤ p / 2` and `b ≤ p / 2` such that `a ^ 2 + b ^ 2 ≡ x [MOD p]`. This is a version of
+`ZMod.sq_add_sq` with estimates on `a` and `b`. -/
+theorem Nat.sq_add_sq_modEq (p : ℕ) [Fact p.Prime] (x : ℕ) :
+    ∃ a b : ℕ, a ≤ p / 2 ∧ b ≤ p / 2 ∧ a ^ 2 + b ^ 2 ≡ x [MOD p] := by
+  simpa only [← Int.coe_nat_modEq_iff] using Nat.sq_add_sq_zmodEq p x
+
 namespace CharP
 
 theorem sq_add_sq (R : Type _) [CommRing R] [IsDomain R] (p : ℕ) [NeZero p] [CharP R p] (x : ℤ) :
feat: port FieldTheory.Finite.Basic (#4583)

Dependencies 10 + 659

660 files ported (98.5%)
275454 lines ported (98.8%)
Show graph

The unported dependencies are