-
Notifications
You must be signed in to change notification settings - Fork 251
/
Order.lean
348 lines (297 loc) · 13.4 KB
/
Order.lean
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
/-
Copyright (c) 2019 Johan Commelin. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Johan Commelin, Kenny Lau
-/
import Mathlib.RingTheory.PowerSeries.Basic
import Mathlib.Algebra.CharP.Basic
#align_import ring_theory.power_series.basic from "leanprover-community/mathlib"@"2d5739b61641ee4e7e53eca5688a08f66f2e6a60"
/-! # Formal power series (in one variable) - Order
The `PowerSeries.order` of a formal power series `φ` is the multiplicity of the variable `X` in `φ`.
If the coefficients form an integral domain, then `PowerSeries.order` is an
additive valuation (`PowerSeries.order_mul`, `PowerSeries.le_order_add`).
We prove that if the commutative ring `R` of coefficients is an integral domain,
then the ring `R⟦X⟧` of formal power series in one variable over `R`
is an integral domain.
-/
noncomputable section
open BigOperators Polynomial
open Finset (antidiagonal mem_antidiagonal)
namespace PowerSeries
open Finsupp (single)
variable {R : Type*}
section OrderBasic
open multiplicity
variable [Semiring R] {φ : R⟦X⟧}
theorem exists_coeff_ne_zero_iff_ne_zero : (∃ n : ℕ, coeff R n φ ≠ 0) ↔ φ ≠ 0 := by
refine' not_iff_not.mp _
push_neg
-- FIXME: the `FunLike.coe` doesn't seem to be picked up in the expression after #8386?
simp [PowerSeries.ext_iff, (coeff R _).map_zero]
#align power_series.exists_coeff_ne_zero_iff_ne_zero PowerSeries.exists_coeff_ne_zero_iff_ne_zero
/-- The order of a formal power series `φ` is the greatest `n : PartENat`
such that `X^n` divides `φ`. The order is `⊤` if and only if `φ = 0`. -/
def order (φ : R⟦X⟧) : PartENat :=
letI := Classical.decEq R
letI := Classical.decEq R⟦X⟧
if h : φ = 0 then ⊤ else Nat.find (exists_coeff_ne_zero_iff_ne_zero.mpr h)
#align power_series.order PowerSeries.order
/-- The order of the `0` power series is infinite.-/
@[simp]
theorem order_zero : order (0 : R⟦X⟧) = ⊤ :=
dif_pos rfl
#align power_series.order_zero PowerSeries.order_zero
theorem order_finite_iff_ne_zero : (order φ).Dom ↔ φ ≠ 0 := by
simp only [order]
constructor
· split_ifs with h <;> intro H
· simp only [PartENat.top_eq_none, Part.not_none_dom] at H
· exact h
· intro h
simp [h]
#align power_series.order_finite_iff_ne_zero PowerSeries.order_finite_iff_ne_zero
/-- If the order of a formal power series is finite,
then the coefficient indexed by the order is nonzero.-/
theorem coeff_order (h : (order φ).Dom) : coeff R (φ.order.get h) φ ≠ 0 := by
classical
simp only [order, order_finite_iff_ne_zero.mp h, not_false_iff, dif_neg, PartENat.get_natCast']
generalize_proofs h
exact Nat.find_spec h
#align power_series.coeff_order PowerSeries.coeff_order
/-- If the `n`th coefficient of a formal power series is nonzero,
then the order of the power series is less than or equal to `n`.-/
theorem order_le (n : ℕ) (h : coeff R n φ ≠ 0) : order φ ≤ n := by
classical
rw [order, dif_neg]
· simp only [PartENat.coe_le_coe]
exact Nat.find_le h
· exact exists_coeff_ne_zero_iff_ne_zero.mp ⟨n, h⟩
#align power_series.order_le PowerSeries.order_le
/-- The `n`th coefficient of a formal power series is `0` if `n` is strictly
smaller than the order of the power series.-/
theorem coeff_of_lt_order (n : ℕ) (h : ↑n < order φ) : coeff R n φ = 0 := by
contrapose! h
exact order_le _ h
#align power_series.coeff_of_lt_order PowerSeries.coeff_of_lt_order
/-- The `0` power series is the unique power series with infinite order.-/
@[simp]
theorem order_eq_top {φ : R⟦X⟧} : φ.order = ⊤ ↔ φ = 0 := by
constructor
· intro h
ext n
rw [(coeff R n).map_zero, coeff_of_lt_order]
simp [h]
· rintro rfl
exact order_zero
#align power_series.order_eq_top PowerSeries.order_eq_top
/-- The order of a formal power series is at least `n` if
the `i`th coefficient is `0` for all `i < n`.-/
theorem nat_le_order (φ : R⟦X⟧) (n : ℕ) (h : ∀ i < n, coeff R i φ = 0) : ↑n ≤ order φ := by
by_contra H; rw [not_le] at H
have : (order φ).Dom := PartENat.dom_of_le_natCast H.le
rw [← PartENat.natCast_get this, PartENat.coe_lt_coe] at H
exact coeff_order this (h _ H)
#align power_series.nat_le_order PowerSeries.nat_le_order
/-- The order of a formal power series is at least `n` if
the `i`th coefficient is `0` for all `i < n`.-/
theorem le_order (φ : R⟦X⟧) (n : PartENat) (h : ∀ i : ℕ, ↑i < n → coeff R i φ = 0) :
n ≤ order φ := by
induction n using PartENat.casesOn
· show _ ≤ _
rw [top_le_iff, order_eq_top]
ext i
exact h _ (PartENat.natCast_lt_top i)
· apply nat_le_order
simpa only [PartENat.coe_lt_coe] using h
#align power_series.le_order PowerSeries.le_order
/-- The order of a formal power series is exactly `n` if the `n`th coefficient is nonzero,
and the `i`th coefficient is `0` for all `i < n`.-/
theorem order_eq_nat {φ : R⟦X⟧} {n : ℕ} :
order φ = n ↔ coeff R n φ ≠ 0 ∧ ∀ i, i < n → coeff R i φ = 0 := by
classical
rcases eq_or_ne φ 0 with (rfl | hφ)
· simpa [(coeff R _).map_zero] using (PartENat.natCast_ne_top _).symm
simp [order, dif_neg hφ, Nat.find_eq_iff]
#align power_series.order_eq_nat PowerSeries.order_eq_nat
/-- The order of a formal power series is exactly `n` if the `n`th coefficient is nonzero,
and the `i`th coefficient is `0` for all `i < n`.-/
theorem order_eq {φ : R⟦X⟧} {n : PartENat} :
order φ = n ↔ (∀ i : ℕ, ↑i = n → coeff R i φ ≠ 0) ∧ ∀ i : ℕ, ↑i < n → coeff R i φ = 0 := by
induction n using PartENat.casesOn
· rw [order_eq_top]
constructor
· rintro rfl
constructor <;> intros
· exfalso
exact PartENat.natCast_ne_top ‹_› ‹_›
· exact (coeff _ _).map_zero
· rintro ⟨_h₁, h₂⟩
ext i
exact h₂ i (PartENat.natCast_lt_top i)
· simpa [PartENat.natCast_inj] using order_eq_nat
#align power_series.order_eq PowerSeries.order_eq
/-- The order of the sum of two formal power series
is at least the minimum of their orders.-/
theorem le_order_add (φ ψ : R⟦X⟧) : min (order φ) (order ψ) ≤ order (φ + ψ) := by
refine' le_order _ _ _
simp (config := { contextual := true }) [coeff_of_lt_order]
#align power_series.le_order_add PowerSeries.le_order_add
private theorem order_add_of_order_eq.aux (φ ψ : R⟦X⟧) (_h : order φ ≠ order ψ)
(H : order φ < order ψ) : order (φ + ψ) ≤ order φ ⊓ order ψ := by
suffices order (φ + ψ) = order φ by
rw [le_inf_iff, this]
exact ⟨le_rfl, le_of_lt H⟩
· rw [order_eq]
constructor
· intro i hi
rw [← hi] at H
rw [(coeff _ _).map_add, coeff_of_lt_order i H, add_zero]
exact (order_eq_nat.1 hi.symm).1
· intro i hi
rw [(coeff _ _).map_add, coeff_of_lt_order i hi, coeff_of_lt_order i (lt_trans hi H),
zero_add]
-- #align power_series.order_add_of_order_eq.aux power_series.order_add_of_order_eq.aux
/-- The order of the sum of two formal power series
is the minimum of their orders if their orders differ.-/
theorem order_add_of_order_eq (φ ψ : R⟦X⟧) (h : order φ ≠ order ψ) :
order (φ + ψ) = order φ ⊓ order ψ := by
refine' le_antisymm _ (le_order_add _ _)
by_cases H₁ : order φ < order ψ
· apply order_add_of_order_eq.aux _ _ h H₁
by_cases H₂ : order ψ < order φ
· simpa only [add_comm, inf_comm] using order_add_of_order_eq.aux _ _ h.symm H₂
exfalso; exact h (le_antisymm (not_lt.1 H₂) (not_lt.1 H₁))
#align power_series.order_add_of_order_eq PowerSeries.order_add_of_order_eq
/-- The order of the product of two formal power series
is at least the sum of their orders.-/
theorem order_mul_ge (φ ψ : R⟦X⟧) : order φ + order ψ ≤ order (φ * ψ) := by
apply le_order
intro n hn; rw [coeff_mul, Finset.sum_eq_zero]
rintro ⟨i, j⟩ hij
by_cases hi : ↑i < order φ
· rw [coeff_of_lt_order i hi, zero_mul]
by_cases hj : ↑j < order ψ
· rw [coeff_of_lt_order j hj, mul_zero]
rw [not_lt] at hi hj; rw [mem_antidiagonal] at hij
exfalso
apply ne_of_lt (lt_of_lt_of_le hn <| add_le_add hi hj)
rw [← Nat.cast_add, hij]
#align power_series.order_mul_ge PowerSeries.order_mul_ge
/-- The order of the monomial `a*X^n` is infinite if `a = 0` and `n` otherwise.-/
theorem order_monomial (n : ℕ) (a : R) [Decidable (a = 0)] :
order (monomial R n a) = if a = 0 then (⊤ : PartENat) else n := by
split_ifs with h
· rw [h, order_eq_top, LinearMap.map_zero]
· rw [order_eq]
constructor <;> intro i hi
· rw [PartENat.natCast_inj] at hi
rwa [hi, coeff_monomial_same]
· rw [PartENat.coe_lt_coe] at hi
rw [coeff_monomial, if_neg]
exact ne_of_lt hi
#align power_series.order_monomial PowerSeries.order_monomial
/-- The order of the monomial `a*X^n` is `n` if `a ≠ 0`.-/
theorem order_monomial_of_ne_zero (n : ℕ) (a : R) (h : a ≠ 0) : order (monomial R n a) = n := by
classical
rw [order_monomial, if_neg h]
#align power_series.order_monomial_of_ne_zero PowerSeries.order_monomial_of_ne_zero
/-- If `n` is strictly smaller than the order of `ψ`, then the `n`th coefficient of its product
with any other power series is `0`. -/
theorem coeff_mul_of_lt_order {φ ψ : R⟦X⟧} {n : ℕ} (h : ↑n < ψ.order) :
coeff R n (φ * ψ) = 0 := by
suffices coeff R n (φ * ψ) = ∑ p in antidiagonal n, 0 by rw [this, Finset.sum_const_zero]
rw [coeff_mul]
apply Finset.sum_congr rfl
intro x hx
refine' mul_eq_zero_of_right (coeff R x.fst φ) (coeff_of_lt_order x.snd (lt_of_le_of_lt _ h))
rw [mem_antidiagonal] at hx
norm_cast
omega
#align power_series.coeff_mul_of_lt_order PowerSeries.coeff_mul_of_lt_order
theorem coeff_mul_one_sub_of_lt_order {R : Type*} [CommRing R] {φ ψ : R⟦X⟧} (n : ℕ)
(h : ↑n < ψ.order) : coeff R n (φ * (1 - ψ)) = coeff R n φ := by
simp [coeff_mul_of_lt_order h, mul_sub]
#align power_series.coeff_mul_one_sub_of_lt_order PowerSeries.coeff_mul_one_sub_of_lt_order
theorem coeff_mul_prod_one_sub_of_lt_order {R ι : Type*} [CommRing R] (k : ℕ) (s : Finset ι)
(φ : R⟦X⟧) (f : ι → R⟦X⟧) :
(∀ i ∈ s, ↑k < (f i).order) → coeff R k (φ * ∏ i in s, (1 - f i)) = coeff R k φ := by
classical
induction' s using Finset.induction_on with a s ha ih t
· simp
· intro t
simp only [Finset.mem_insert, forall_eq_or_imp] at t
rw [Finset.prod_insert ha, ← mul_assoc, mul_right_comm, coeff_mul_one_sub_of_lt_order _ t.1]
exact ih t.2
#align power_series.coeff_mul_prod_one_sub_of_lt_order PowerSeries.coeff_mul_prod_one_sub_of_lt_order
-- TODO: link with `X_pow_dvd_iff`
theorem X_pow_order_dvd (h : (order φ).Dom) : X ^ (order φ).get h ∣ φ := by
refine' ⟨PowerSeries.mk fun n => coeff R (n + (order φ).get h) φ, _⟩
ext n
simp only [coeff_mul, coeff_X_pow, coeff_mk, boole_mul, Finset.sum_ite,
Finset.sum_const_zero, add_zero]
rw [Finset.filter_fst_eq_antidiagonal n (Part.get (order φ) h)]
split_ifs with hn
· simp [tsub_add_cancel_of_le hn]
· simp only [Finset.sum_empty]
refine' coeff_of_lt_order _ _
simpa [PartENat.coe_lt_iff] using fun _ => hn
set_option linter.uppercaseLean3 false in
#align power_series.X_pow_order_dvd PowerSeries.X_pow_order_dvd
theorem order_eq_multiplicity_X {R : Type*} [Semiring R] [@DecidableRel R⟦X⟧ (· ∣ ·)] (φ : R⟦X⟧) :
order φ = multiplicity X φ := by
classical
rcases eq_or_ne φ 0 with (rfl | hφ)
· simp
induction' ho : order φ using PartENat.casesOn with n
· simp [hφ] at ho
have hn : φ.order.get (order_finite_iff_ne_zero.mpr hφ) = n := by simp [ho]
rw [← hn]
refine'
le_antisymm (le_multiplicity_of_pow_dvd <| X_pow_order_dvd (order_finite_iff_ne_zero.mpr hφ))
(PartENat.find_le _ _ _)
rintro ⟨ψ, H⟩
have := congr_arg (coeff R n) H
rw [← (ψ.commute_X.pow_right _).eq, coeff_mul_of_lt_order, ← hn] at this
· exact coeff_order _ this
· rw [X_pow_eq, order_monomial]
split_ifs
· exact PartENat.natCast_lt_top _
· rw [← hn, PartENat.coe_lt_coe]
exact Nat.lt_succ_self _
set_option linter.uppercaseLean3 false in
#align power_series.order_eq_multiplicity_X PowerSeries.order_eq_multiplicity_X
end OrderBasic
section OrderZeroNeOne
variable [Semiring R] [Nontrivial R]
/-- The order of the formal power series `1` is `0`.-/
@[simp]
theorem order_one : order (1 : R⟦X⟧) = 0 := by
simpa using order_monomial_of_ne_zero 0 (1 : R) one_ne_zero
#align power_series.order_one PowerSeries.order_one
/-- The order of the formal power series `X` is `1`.-/
@[simp]
theorem order_X : order (X : R⟦X⟧) = 1 := by
simpa only [Nat.cast_one] using order_monomial_of_ne_zero 1 (1 : R) one_ne_zero
set_option linter.uppercaseLean3 false in
#align power_series.order_X PowerSeries.order_X
/-- The order of the formal power series `X^n` is `n`.-/
@[simp]
theorem order_X_pow (n : ℕ) : order ((X : R⟦X⟧) ^ n) = n := by
rw [X_pow_eq, order_monomial_of_ne_zero]
exact one_ne_zero
set_option linter.uppercaseLean3 false in
#align power_series.order_X_pow PowerSeries.order_X_pow
end OrderZeroNeOne
section OrderIsDomain
-- TODO: generalize to `[Semiring R] [NoZeroDivisors R]`
variable [CommRing R] [IsDomain R]
/-- The order of the product of two formal power series over an integral domain
is the sum of their orders.-/
theorem order_mul (φ ψ : R⟦X⟧) : order (φ * ψ) = order φ + order ψ := by
classical
simp_rw [order_eq_multiplicity_X]
exact multiplicity.mul X_prime
#align power_series.order_mul PowerSeries.order_mul
end OrderIsDomain
end PowerSeries
end