-
Notifications
You must be signed in to change notification settings - Fork 1.2k
Expand file tree
/
Copy pathExponential.lean
More file actions
698 lines (540 loc) Β· 31 KB
/
Exponential.lean
File metadata and controls
698 lines (540 loc) Β· 31 KB
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
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
/-
Copyright (c) 2021 Anatole Dedecker. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Anatole Dedecker, Eric Wieser, Yuyang Zhao
-/
module
public import Mathlib.Algebra.Algebra.TransferInstance
public import Mathlib.Algebra.Ring.Action.ConjAct
public import Mathlib.Analysis.Analytic.ChangeOrigin
public import Mathlib.Analysis.Complex.Basic
public import Mathlib.Data.Nat.Choose.Cast
public import Mathlib.Analysis.Analytic.OfScalars
/-!
# Exponential in a Banach algebra
In this file, we define `NormedSpace.exp : πΈ β πΈ`,
the exponential map in a topological algebra `πΈ`.
While for most interesting results we need `πΈ` to be normed algebra, we do not require this in the
definition in order to make `NormedSpace.exp` independent of a particular choice of norm. The
definition also does not require that `πΈ` be complete, but we need to assume it for most results.
We then prove some basic results, but we avoid importing derivatives here to minimize dependencies.
Results involving derivatives and comparisons with `Real.exp` and `Complex.exp` can be found in
`Analysis.SpecialFunctions.Exponential`.
## Main results
We prove most result for an arbitrary field `π`, and then specialize to `π = β` or `π = β`.
### General case
- `NormedSpace.exp_add_of_commute_of_mem_ball` : if `π` has characteristic zero,
then given two commuting elements `x` and `y` in the disk of convergence, we have
`NormedSpace.exp (x+y) = (NormedSpace.exp x) * (NormedSpace.exp y)`
- `NormedSpace.exp_add_of_mem_ball` : if `π` has characteristic zero and `πΈ` is commutative,
then given two elements `x` and `y` in the disk of convergence, we have
`NormedSpace.exp (x+y) = (NormedSpace.exp x) * (NormedSpace.exp y)`
- `NormedSpace.exp_neg_of_mem_ball` : if `π` has characteristic zero and `πΈ` is a division ring,
then given an element `x` in the disk of convergence,
we have `NormedSpace.exp (-x) = (NormedSpace.exp x)β»ΒΉ`.
### `π = β` or `π = β`
- `expSeries_radius_eq_top` : the `FormalMultilinearSeries` defining `NormedSpace.exp`
has infinite radius of convergence
- `NormedSpace.exp_add_of_commute` : given two commuting elements `x` and `y`, we have
`NormedSpace.exp (x+y) = (NormedSpace.exp x) * (NormedSpace.exp y)`
- `NormedSpace.exp_add` : if `πΈ` is commutative, then we have
`NormedSpace.exp (x+y) = (NormedSpace.exp x) * (NormedSpace.exp y)` for any `x` and `y`
- `NormedSpace.exp_neg` : if `πΈ` is a division ring, then we have
`NormedSpace.exp (-x) = (NormedSpace.exp x)β»ΒΉ`.
- `NormedSpace.exp_sum_of_commute` : the analogous result to `NormedSpace.exp_add_of_commute`
for `Finset.sum`.
- `NormedSpace.exp_sum` : the analogous result to `NormedSpace.exp_add` for `Finset.sum`.
- `NormedSpace.exp_nsmul` : repeated addition in the domain corresponds to
repeated multiplication in the codomain.
- `NormedSpace.exp_zsmul` : repeated addition in the domain corresponds to
repeated multiplication in the codomain.
### Notes
We put nearly all the statements in this file in the `NormedSpace` namespace,
to avoid collisions with the `Real` or `Complex` namespaces.
As of 2023-11-16 due to bad instances in Mathlib
```
import Mathlib
open Real
#time example (x : β) : 0 < exp x := exp_pos _ -- 250ms
#time example (x : β) : 0 < Real.exp x := exp_pos _ -- 2ms
```
This is because `exp x` tries the `NormedSpace.exp π : πΈ β πΈ` function previously defined here,
and generates a slow coercion search from `Real` to `Type`, to fit the first argument here.
We will resolve this slow coercion separately,
but we want to move `exp` out of the root namespace in any case to avoid this ambiguity.
To avoid explicitly passing the base field `π`, we currently fix `π = β` in the definition of
`NormedSpace.exp : πΈ β πΈ`. If `πΈ` can be equipped with a `β`-algebra structure, we use
`Classical.choice` to pick the unique `Algebra β πΈ` instead of requiring an instance argument.
This eliminates the need to provide `Algebra β πΈ` every time `exp` is used. If `πΈ` can't be equipped
with a `β`-algebra structure, we use the junk value `1`.
In the long term it may be possible to replace `Real.exp` and `Complex.exp` with `NormedSpace.exp`
and move it back to the root namespace.
-/
@[expose] public section
namespace NormedSpace
open Filter RCLike ContinuousMultilinearMap NormedField Asymptotics FormalMultilinearSeries
open scoped Nat Topology ENNReal Ring
section TopologicalAlgebra
variable (π πΈ : Type*) [Field π] [Ring πΈ] [Algebra π πΈ] [TopologicalSpace πΈ] [IsTopologicalRing πΈ]
/-- `expSeries π πΈ` is the `FormalMultilinearSeries` whose `n`-th term is the map
`(xα΅’) : πΈβΏ β¦ (1/n! : π) β’ β xα΅’`. Its sum is the exponential map `NormedSpace.exp : πΈ β πΈ`. -/
def expSeries : FormalMultilinearSeries π πΈ πΈ := fun n =>
(n !β»ΒΉ : π) β’ ContinuousMultilinearMap.mkPiAlgebraFin π n πΈ
/-- The exponential series as an `ofScalars` series. -/
theorem expSeries_eq_ofScalars : expSeries π πΈ = ofScalars πΈ fun n β¦ (n !β»ΒΉ : π) := by
simp_rw [FormalMultilinearSeries.ext_iff, expSeries, ofScalars, implies_true]
variable {π πΈ}
open scoped Classical in
/-- `NormedSpace.exp : πΈ β πΈ` is the exponential map. It is defined as the sum of the
`FormalMultilinearSeries` `expSeries β πΈ`.
If `πΈ` can't be equipped with a `β`-algebra structure, we use the junk value `1`. For details on why
this approach is taken, see the module documentation for
`Mathlib/Analysis/Normed/Algebra/Exponential.lean`.
Note that when `πΈ = Matrix n n π`, this is the **Matrix Exponential**; see
`Mathlib/Analysis/Normed/Algebra/MatrixExponential.lean` for lemmas
specific to that case. -/
noncomputable irreducible_def exp (x : πΈ) : πΈ :=
if h : Nonempty (Algebra β πΈ) then
letI _ := h.some
(NormedSpace.expSeries β πΈ).sum x
else
1
/-- The junk value when `πΈ` can't be equipped with a `β`-algebra structure. -/
@[simp]
theorem exp_of_isEmpty_algebra_rat [IsEmpty (Algebra β πΈ)] (x : πΈ) : exp x = 1 := by
rw [exp, dif_neg (not_nonempty_iff.mpr βΉ_βΊ)]
theorem expSeries_apply_eq (x : πΈ) (n : β) :
(expSeries π πΈ n fun _ => x) = (n !β»ΒΉ : π) β’ x ^ n := by simp [expSeries]
theorem expSeries_apply_eq' (x : πΈ) :
(fun n => expSeries π πΈ n fun _ => x) = fun n => (n !β»ΒΉ : π) β’ x ^ n :=
funext (expSeries_apply_eq x)
theorem expSeries_sum_eq (x : πΈ) : (expSeries π πΈ).sum x = β' n : β, (n !β»ΒΉ : π) β’ x ^ n :=
tsum_congr fun n => expSeries_apply_eq x n
theorem expSeries_sum_eq_rat [Algebra β πΈ] : (expSeries π πΈ).sum = (expSeries β πΈ).sum := by
ext; simp_rw [expSeries_sum_eq, inv_natCast_smul_eq π β]
theorem expSeries_eq_expSeries_rat [Algebra β πΈ] (n : β) :
β(expSeries π πΈ n) = expSeries β πΈ n := by
ext c
simp [expSeries, inv_natCast_smul_eq π β]
variable (π) in
theorem exp_eq_expSeries_sum [CharZero π] : exp = (expSeries π πΈ).sum := by
ext x
rw [exp, dif_pos β¨RestrictScalars.algebra β π πΈβ©, β @expSeries_sum_eq_rat (π := π)]
variable (π) in
theorem exp_eq_tsum [CharZero π] : exp = fun x : πΈ => β' n : β, (n !β»ΒΉ : π) β’ x ^ n := by
rw [exp_eq_expSeries_sum π]
ext x
exact expSeries_sum_eq x
theorem exp_eq_tsum_rat [Algebra β πΈ] : exp = fun x : πΈ => β' n : β, (n !β»ΒΉ : β) β’ x ^ n :=
exp_eq_tsum β
variable (π) in
/-- The exponential sum as an `ofScalarsSum`. -/
theorem exp_eq_ofScalarsSum [CharZero π] :
exp = ofScalarsSum (E := πΈ) fun n β¦ (n !β»ΒΉ : π) := by
rw [exp_eq_tsum π, ofScalarsSum_eq_tsum]
theorem expSeries_apply_zero (n : β) :
expSeries π πΈ n (fun _ => (0 : πΈ)) = Pi.single (M := fun _ => πΈ) 0 1 n := by
rw [expSeries_apply_eq]
rcases n with - | n
Β· simp
Β· rw [zero_pow (Nat.succ_ne_zero _), smul_zero, Pi.single_eq_of_ne n.succ_ne_zero]
@[simp]
theorem exp_zero : exp (0 : πΈ) = 1 := by
rw [exp]
split_ifs
Β· simp_rw [expSeries_sum_eq, β expSeries_apply_eq, expSeries_apply_zero, tsum_pi_single]
Β· rfl
@[simp]
theorem exp_op [T2Space πΈ] (x : πΈ) :
exp (MulOpposite.op x) = MulOpposite.op (exp x) := by
obtain h | β¨β¨_β©β© := isEmpty_or_nonempty (Algebra β πΈ)
Β· have : IsEmpty (Algebra β πΈα΅α΅α΅) := β¨fun _ => h.elim <| (RingEquiv.opOp πΈ).algebra ββ©
simp
Β· rw [exp_eq_tsum β, exp_eq_tsum β]
simp_rw [β MulOpposite.op_pow, β MulOpposite.op_smul, tsum_op]
@[simp]
theorem exp_unop [T2Space πΈ] (x : πΈα΅α΅α΅) :
exp (MulOpposite.unop x) = MulOpposite.unop (exp x) := by
induction x; simp
theorem star_exp [T2Space πΈ] [StarRing πΈ] [ContinuousStar πΈ] (x : πΈ) :
star (exp x) = exp (star x) := by
obtain _ | β¨β¨_β©β© := isEmpty_or_nonempty (Algebra β πΈ)
Β· simp
Β· simp_rw [exp_eq_tsum β, β star_pow, β star_inv_natCast_smul, β tsum_star]
/-- A subalgebra of `πΈ` that is closed topologically and under `β`-scaling is closed under `exp`. -/
theorem exp_mem
{R S : Type*} [Monoid R] [SMul β R] [MulAction R πΈ] [Algebra β πΈ] [IsScalarTower β R πΈ]
[SetLike S πΈ] [SubsemiringClass S πΈ] [SMulMemClass S R πΈ] {s : S}
(h_closed : IsClosed (s : Set πΈ)) {x : πΈ} (h : x β s) :
exp x β s := by
have := SMulMemClass.ofIsScalarTower S β R πΈ
rw [exp_eq_tsum β]
exact tsum_mem h_closed fun i => SMulMemClass.smul_mem _ <| pow_mem h _
variable (π)
@[aesop safe apply]
theorem _root_.IsSelfAdjoint.exp [T2Space πΈ] [StarRing πΈ] [ContinuousStar πΈ] {x : πΈ}
(h : IsSelfAdjoint x) : IsSelfAdjoint (exp x) :=
(star_exp x).trans <| h.symm βΈ rfl
theorem _root_.Commute.exp_right [T2Space πΈ] {x y : πΈ} (h : Commute x y) :
Commute x (exp y) := by
obtain _ | β¨β¨_β©β© := isEmpty_or_nonempty (Algebra β πΈ)
Β· simp
Β· rw [exp_eq_tsum β]
exact Commute.tsum_right x fun n => (h.pow_right n).smul_right _
theorem _root_.Commute.exp_left [T2Space πΈ] {x y : πΈ} (h : Commute x y) :
Commute (exp x) y :=
h.symm.exp_right.symm
theorem _root_.Commute.exp [T2Space πΈ] {x y : πΈ} (h : Commute x y) :
Commute (exp x) (exp y) :=
h.exp_left.exp_right
end TopologicalAlgebra
section TopologicalDivisionAlgebra
variable {π πΈ : Type*} [Field π] [DivisionRing πΈ] [Algebra π πΈ] [TopologicalSpace πΈ]
[IsTopologicalRing πΈ]
theorem expSeries_apply_eq_div (x : πΈ) (n : β) : (expSeries π πΈ n fun _ => x) = x ^ n / n ! := by
rw [div_eq_mul_inv, β (Nat.cast_commute n ! (x ^ n)).inv_leftβ.eq, β smul_eq_mul,
expSeries_apply_eq, inv_natCast_smul_eq π πΈ]
theorem expSeries_apply_eq_div' (x : πΈ) :
(fun n => expSeries π πΈ n fun _ => x) = fun n => x ^ n / n ! :=
funext (expSeries_apply_eq_div x)
theorem expSeries_sum_eq_div (x : πΈ) : (expSeries π πΈ).sum x = β' n : β, x ^ n / n ! :=
tsum_congr (expSeries_apply_eq_div x)
theorem exp_eq_tsum_div [CharZero πΈ] : exp = fun x : πΈ => β' n : β, x ^ n / n ! := by
rw [exp_eq_expSeries_sum β]
ext x
exact expSeries_sum_eq_div x
end TopologicalDivisionAlgebra
section Normed
section AnyFieldAnyAlgebra
variable {π πΈ πΉ : Type*} [NontriviallyNormedField π]
variable [NormedRing πΈ] [NormedRing πΉ] [NormedAlgebra π πΈ]
theorem norm_expSeries_summable_of_mem_ball (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
Summable fun n => βexpSeries π πΈ n fun _ => xβ :=
(expSeries π πΈ).summable_norm_apply hx
theorem norm_expSeries_summable_of_mem_ball' (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
Summable fun n => β(n !β»ΒΉ : π) β’ x ^ nβ := by
change Summable (norm β _)
rw [β expSeries_apply_eq']
exact norm_expSeries_summable_of_mem_ball x hx
section CompleteAlgebra
variable [CompleteSpace πΈ]
theorem expSeries_summable_of_mem_ball (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
Summable fun n => expSeries π πΈ n fun _ => x :=
(norm_expSeries_summable_of_mem_ball x hx).of_norm
theorem expSeries_summable_of_mem_ball' (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
Summable fun n => (n !β»ΒΉ : π) β’ x ^ n :=
(norm_expSeries_summable_of_mem_ball' x hx).of_norm
theorem expSeries_hasSum_exp_of_mem_ball [CharZero π] (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
HasSum (fun n => expSeries π πΈ n fun _ => x) (exp x) := by
simpa only [exp_eq_expSeries_sum π, expSeries_sum_eq_rat] using
FormalMultilinearSeries.hasSum (expSeries π πΈ) hx
theorem expSeries_hasSum_exp_of_mem_ball' [CharZero π] (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
HasSum (fun n => (n !β»ΒΉ : π) β’ x ^ n) (exp x) := by
rw [β expSeries_apply_eq']
exact expSeries_hasSum_exp_of_mem_ball x hx
theorem hasFPowerSeriesOnBall_exp_of_radius_pos [CharZero π] (h : 0 < (expSeries π πΈ).radius) :
HasFPowerSeriesOnBall exp (expSeries π πΈ) 0 (expSeries π πΈ).radius := by
simpa only [exp_eq_expSeries_sum π, expSeries_sum_eq_rat] using
(expSeries π πΈ).hasFPowerSeriesOnBall h
theorem hasFPowerSeriesAt_exp_zero_of_radius_pos [CharZero π] (h : 0 < (expSeries π πΈ).radius) :
HasFPowerSeriesAt exp (expSeries π πΈ) 0 := by
simpa only [exp, expSeries_sum_eq_rat] using
(hasFPowerSeriesOnBall_exp_of_radius_pos h).hasFPowerSeriesAt
theorem continuousOn_exp [CharZero π] :
ContinuousOn (exp : πΈ β πΈ) (Metric.eball 0 (expSeries π πΈ).radius) := by
have := FormalMultilinearSeries.continuousOn (p := expSeries π πΈ)
simpa only [exp_eq_expSeries_sum π, expSeries_sum_eq_rat] using this
theorem analyticAt_exp_of_mem_ball [CharZero π] (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) : AnalyticAt π exp x := by
by_cases h : (expSeries π πΈ).radius = 0
Β· rw [h] at hx; exact (ENNReal.not_lt_zero hx).elim
Β· have h := pos_iff_ne_zero.mpr h
exact (hasFPowerSeriesOnBall_exp_of_radius_pos h).analyticAt_of_mem hx
/-- In a Banach-algebra `πΈ` over a normed field `π` of characteristic zero, if `x` and `y` are
in the disk of convergence and commute, then
`NormedSpace.exp (x + y) = (NormedSpace.exp x) * (NormedSpace.exp y)`. -/
theorem exp_add_of_commute_of_mem_ball [CharZero π] {x y : πΈ} (hxy : Commute x y)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius)
(hy : y β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) : exp (x + y) = exp x * exp y := by
rw [exp_eq_tsum π,
tsum_mul_tsum_eq_tsum_sum_antidiagonal_of_summable_norm
(norm_expSeries_summable_of_mem_ball' x hx) (norm_expSeries_summable_of_mem_ball' y hy)]
dsimp only
conv_lhs =>
congr
ext
rw [hxy.add_pow' _, Finset.smul_sum]
refine tsum_congr fun n => Finset.sum_congr rfl fun kl hkl => ?_
rw [β Nat.cast_smul_eq_nsmul π, smul_smul, smul_mul_smul_comm, β Finset.mem_antidiagonal.mp hkl,
Nat.cast_add_choose, Finset.mem_antidiagonal.mp hkl]
field_simp [n.factorial_ne_zero]
/-- `NormedSpace.exp x` has explicit two-sided inverse `NormedSpace.exp (-x)`. -/
@[implicit_reducible]
noncomputable def invertibleExpOfMemBall [CharZero π] {x : πΈ}
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) : Invertible (exp x)
where
invOf := exp (-x)
invOf_mul_self := by
have hnx : -x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius := by
rw [Metric.mem_eball, β neg_zero, edist_neg_neg]
exact hx
rw [β exp_add_of_commute_of_mem_ball (Commute.neg_left <| Commute.refl x) hnx hx,
neg_add_cancel, exp_zero]
mul_invOf_self := by
have hnx : -x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius := by
rw [Metric.mem_eball, β neg_zero, edist_neg_neg]
exact hx
rw [β exp_add_of_commute_of_mem_ball (Commute.neg_right <| Commute.refl x) hx hnx,
add_neg_cancel, exp_zero]
theorem isUnit_exp_of_mem_ball [CharZero π] {x : πΈ}
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) : IsUnit (exp x) :=
@isUnit_of_invertible _ _ _ (invertibleExpOfMemBall hx)
theorem invOf_exp_of_mem_ball [CharZero π] {x : πΈ}
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) [Invertible (exp x)] :
β
(exp x) = exp (-x) := by
letI := invertibleExpOfMemBall hx; convert (rfl : β
(exp x) = _)
/-- Any continuous ring homomorphism commutes with `NormedSpace.exp`. -/
theorem map_exp_of_mem_ball [Algebra π πΉ] [CharZero π] {F} [FunLike F πΈ πΉ] [RingHomClass F πΈ πΉ]
(f : F) (hf : Continuous f) (x : πΈ) (hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
f (exp x) = exp (f x) := by
rw [exp_eq_tsum π, exp_eq_tsum π]
refine ((expSeries_summable_of_mem_ball' _ hx).hasSum.map f hf).tsum_eq.symm.trans ?_
dsimp only [Function.comp_def]
simp_rw [map_inv_natCast_smul f π π, map_pow]
end CompleteAlgebra
theorem algebraMap_exp_comm_of_mem_ball [CharZero π] [CompleteSpace π] (x : π)
(hx : x β Metric.eball (0 : π) (expSeries π π).radius) :
algebraMap π πΈ (exp x) = exp (algebraMap π πΈ x) :=
map_exp_of_mem_ball (algebraMap _ _) (algebraMapCLM _ _).continuous _ hx
end AnyFieldAnyAlgebra
section AnyFieldDivisionAlgebra
variable {π πΈ : Type*} [NontriviallyNormedField π] [NormedDivisionRing πΈ] [NormedAlgebra π πΈ]
variable (π)
theorem norm_expSeries_div_summable_of_mem_ball (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
Summable fun n => βx ^ n / (n !)β := by
change Summable (norm β _)
rw [β expSeries_apply_eq_div' (π := π) x]
exact norm_expSeries_summable_of_mem_ball x hx
theorem expSeries_div_summable_of_mem_ball [CompleteSpace πΈ] (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) : Summable fun n => x ^ n / n ! :=
(norm_expSeries_div_summable_of_mem_ball π x hx).of_norm
theorem expSeries_div_hasSum_exp_of_mem_ball [CharZero π] [CompleteSpace πΈ] (x : πΈ)
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) :
HasSum (fun n => x ^ n / n !) (exp x) := by
rw [β expSeries_apply_eq_div' (π := π) x]
exact expSeries_hasSum_exp_of_mem_ball x hx
theorem exp_neg_of_mem_ball [CharZero π] [CompleteSpace πΈ] {x : πΈ}
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) : exp (-x) = (exp x)β»ΒΉ :=
letI := invertibleExpOfMemBall hx
invOf_eq_inv (exp x)
end AnyFieldDivisionAlgebra
section AnyFieldCommAlgebra
variable {π πΈ : Type*} [NontriviallyNormedField π] [NormedCommRing πΈ] [NormedAlgebra π πΈ]
[CompleteSpace πΈ]
/-- In a commutative Banach-algebra `πΈ` over a normed field `π` of characteristic zero,
`NormedSpace.exp (x+y) = (NormedSpace.exp x) * (NormedSpace.exp y)`
for all `x`, `y` in the disk of convergence. -/
theorem exp_add_of_mem_ball [CharZero π] {x y : πΈ}
(hx : x β Metric.eball (0 : πΈ) (expSeries π πΈ).radius)
(hy : y β Metric.eball (0 : πΈ) (expSeries π πΈ).radius) : exp (x + y) = exp x * exp y :=
exp_add_of_commute_of_mem_ball (Commute.all x y) hx hy
end AnyFieldCommAlgebra
section AnyAlgebra
variable (π πΈ : Type*) [NontriviallyNormedField π] [CharZero π] [ContinuousSMul β π]
variable [NormedRing πΈ] [NormedAlgebra π πΈ]
/-- In a normed algebra `πΈ` over `π = β` or `π = β`, the series defining the exponential map
has an infinite radius of convergence. -/
theorem expSeries_radius_eq_top : (expSeries π πΈ).radius = β := by
have {n : β} : (Nat.factorial n : π) β 0 := Nat.cast_ne_zero.mpr (Nat.factorial_ne_zero n)
apply expSeries_eq_ofScalars π πΈ βΈ
ofScalars_radius_eq_top_of_tendsto πΈ _ (Eventually.of_forall fun n => ?_)
Β· simp_rw [β norm_div, Nat.factorial_succ, Nat.cast_mul, mul_inv_rev, mul_div_right_comm,
inv_div_inv, norm_mul, div_self this, norm_one, one_mul]
apply norm_zero (E := π) βΈ Filter.Tendsto.norm
apply (Filter.tendsto_add_atTop_iff_nat (f := fun n => (n : π)β»ΒΉ) 1).mpr
exact tendsto_inv_atTop_nhds_zero_nat
Β· simp [this]
theorem expSeries_radius_pos : 0 < (expSeries π πΈ).radius := by
rw [expSeries_radius_eq_top]
exact WithTop.top_pos
variable {π πΈ}
theorem norm_expSeries_summable (x : πΈ) : Summable fun n => βexpSeries π πΈ n fun _ => xβ :=
norm_expSeries_summable_of_mem_ball x ((expSeries_radius_eq_top π πΈ).symm βΈ edist_lt_top _ _)
theorem norm_expSeries_summable' (x : πΈ) : Summable fun n => β(n !β»ΒΉ : π) β’ x ^ nβ :=
norm_expSeries_summable_of_mem_ball' x ((expSeries_radius_eq_top π πΈ).symm βΈ edist_lt_top _ _)
theorem algebraMap_exp_comm [CompleteSpace π] (x : π) :
algebraMap π πΈ (exp x) = exp (algebraMap π πΈ x) :=
algebraMap_exp_comm_of_mem_ball x <| (expSeries_radius_eq_top π π).symm βΈ edist_lt_top _ _
variable [CompleteSpace πΈ]
theorem expSeries_summable (x : πΈ) : Summable fun n => expSeries π πΈ n fun _ => x :=
(norm_expSeries_summable x).of_norm
theorem expSeries_summable' (x : πΈ) : Summable fun n => (n !β»ΒΉ : π) β’ x ^ n :=
(norm_expSeries_summable' x).of_norm
theorem expSeries_hasSum_exp (x : πΈ) : HasSum (fun n => expSeries π πΈ n fun _ => x) (exp x) :=
expSeries_hasSum_exp_of_mem_ball x ((expSeries_radius_eq_top π πΈ).symm βΈ edist_lt_top _ _)
theorem exp_series_hasSum_exp' (x : πΈ) : HasSum (fun n => (n !β»ΒΉ : π) β’ x ^ n) (exp x) :=
expSeries_hasSum_exp_of_mem_ball' x ((expSeries_radius_eq_top π πΈ).symm βΈ edist_lt_top _ _)
theorem exp_hasFPowerSeriesOnBall : HasFPowerSeriesOnBall exp (expSeries π πΈ) 0 β :=
expSeries_radius_eq_top π πΈ βΈ hasFPowerSeriesOnBall_exp_of_radius_pos (expSeries_radius_pos _ _)
theorem exp_hasFPowerSeriesAt_zero : HasFPowerSeriesAt exp (expSeries π πΈ) 0 :=
exp_hasFPowerSeriesOnBall.hasFPowerSeriesAt
theorem exp_analytic (x : πΈ) : AnalyticAt π exp x :=
analyticAt_exp_of_mem_ball x ((expSeries_radius_eq_top π πΈ).symm βΈ edist_lt_top _ _)
end AnyAlgebra
section Rat
variable {πΈ πΉ : Type*} [NormedRing πΈ] [NormedAlgebra β πΈ] [CompleteSpace πΈ] [NormedRing πΉ]
@[continuity, fun_prop]
theorem exp_continuous : Continuous (exp : πΈ β πΈ) := by
rw [β continuousOn_univ, β Metric.eball_top_eq_univ (0 : πΈ), β
expSeries_radius_eq_top β πΈ]
exact continuousOn_exp
open Topology in
lemma _root_.Filter.Tendsto.exp {Ξ± : Type*} {l : Filter Ξ±} {f : Ξ± β πΈ} {a : πΈ}
(hf : Tendsto f l (π a)) :
Tendsto (fun x => exp (f x)) l (π (exp a)) :=
(exp_continuous.tendsto _).comp hf
/-- In a Banach-algebra `πΈ` over `π = β` or `π = β`, if `x` and `y` commute, then
`NormedSpace.exp (x+y) = (NormedSpace.exp x) * (NormedSpace.exp y)`. -/
theorem exp_add_of_commute {x y : πΈ} (hxy : Commute x y) : exp (x + y) = exp x * exp y :=
exp_add_of_commute_of_mem_ball hxy ((expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _)
((expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _)
/-- `NormedSpace.exp x` has explicit two-sided inverse `NormedSpace.exp (-x)`. -/
@[implicit_reducible]
noncomputable def invertibleExp (x : πΈ) : Invertible (exp x) :=
invertibleExpOfMemBall <| (expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _
theorem isUnit_exp (x : πΈ) : IsUnit (exp x) :=
isUnit_exp_of_mem_ball <| (expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _
theorem invOf_exp (x : πΈ) [Invertible (exp x)] : β
(exp x) = exp (-x) :=
invOf_exp_of_mem_ball <| (expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _
theorem _root_.Ring.inverse_exp (x : πΈ) : (exp x)β»ΒΉΚ³ = exp (-x) :=
letI := invertibleExp x
Ring.inverse_invertible _
theorem exp_mem_unitary_of_mem_skewAdjoint [StarRing πΈ] [ContinuousStar πΈ] {x : πΈ}
(h : x β skewAdjoint πΈ) : exp x β unitary πΈ := by
rw [Unitary.mem_iff, star_exp, skewAdjoint.mem_iff.mp h, β
exp_add_of_commute (Commute.refl x).neg_left, β exp_add_of_commute (Commute.refl x).neg_right,
neg_add_cancel, add_neg_cancel, exp_zero, and_self_iff]
lemma _root_.SemiconjBy.exp_right {x a b : πΈ} (h : SemiconjBy x a b) :
SemiconjBy x (exp a) (exp b) := by
rw [exp_eq_tsum β]
apply SemiconjBy.tsum_right x (expSeries_summable' _) (expSeries_summable' _)
exact fun _ β¦ h.pow_right _ |>.smul_right _
lemma _root_.SemiconjBy.exp_neg_mul_mul_exp_eq_self {x a b : πΈ} (h : SemiconjBy x a b) :
exp (-b) * x * exp a = x := by
apply (isUnit_exp b).mul_left_cancel
let hb := invertibleExp b
simp [β invOf_exp, β mul_assoc, h.exp_right.eq]
open scoped Function in -- required for scoped `on` notation
/-- In a Banach-algebra `πΈ` over `π = β` or `π = β`, if a family of elements `f i` mutually
commute then `NormedSpace.exp (β i, f i) = β i, NormedSpace.exp (f i)`. -/
theorem exp_sum_of_commute {ΞΉ} (s : Finset ΞΉ) (f : ΞΉ β πΈ)
(h : (s : Set ΞΉ).Pairwise (Commute on f)) :
exp (β i β s, f i) =
s.noncommProd (fun i => exp (f i)) fun _ hi _ hj _ => (h.of_refl hi hj).exp := by
classical
induction s using Finset.induction_on with
| empty => simp
| insert a s ha ih =>
rw [Finset.noncommProd_insert_of_notMem _ _ _ _ ha, Finset.sum_insert ha, exp_add_of_commute,
ih (h.mono <| Finset.subset_insert _ _)]
refine Commute.sum_right _ _ _ fun i hi => ?_
exact h.of_refl (Finset.mem_insert_self _ _) (Finset.mem_insert_of_mem hi)
theorem exp_nsmul (n : β) (x : πΈ) : exp (n β’ x) = exp x ^ n := by
induction n with
| zero => rw [zero_smul, pow_zero, exp_zero]
| succ n ih => rw [succ_nsmul, pow_succ, exp_add_of_commute ((Commute.refl x).smul_left n), ih]
/-- Any continuous ring homomorphism commutes with `NormedSpace.exp`. -/
theorem map_exp [Algebra β πΉ]
{F} [FunLike F πΈ πΉ] [RingHomClass F πΈ πΉ] (f : F) (hf : Continuous f) (x : πΈ) :
f (exp x) = exp (f x) :=
map_exp_of_mem_ball f hf x <| (expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _
theorem exp_smul {G} [Monoid G] [MulSemiringAction G πΈ] [ContinuousConstSMul G πΈ] (g : G) (x : πΈ) :
exp (g β’ x) = g β’ exp x :=
(map_exp (MulSemiringAction.toRingHom G πΈ g) (continuous_const_smul g) x).symm
theorem exp_units_conj (y : πΈΛ£) (x : πΈ) : exp (y * x * βyβ»ΒΉ : πΈ) = y * exp x * βyβ»ΒΉ :=
exp_smul (ConjAct.toConjAct y) x
theorem exp_units_conj' (y : πΈΛ£) (x : πΈ) : exp (βyβ»ΒΉ * x * y) = βyβ»ΒΉ * exp x * y :=
exp_units_conj _ _
@[simp]
theorem _root_.Prod.fst_exp [NormedAlgebra β πΉ] [CompleteSpace πΉ] (x : πΈ Γ πΉ) :
(exp x).fst = exp x.fst :=
map_exp (RingHom.fst πΈ πΉ) continuous_fst x
@[simp]
theorem _root_.Prod.snd_exp [NormedAlgebra β πΉ] [CompleteSpace πΉ] (x : πΈ Γ πΉ) :
(exp x).snd = exp x.snd :=
map_exp (RingHom.snd πΈ πΉ) continuous_snd x
@[simp]
theorem _root_.Pi.coe_exp {ΞΉ : Type*} {πΈ : ΞΉ β Type*} [Finite ΞΉ] [β i, NormedRing (πΈ i)]
[β i, NormedAlgebra β (πΈ i)] [β i, CompleteSpace (πΈ i)] (x : β i, πΈ i) (i : ΞΉ) :
exp x i = exp (x i) :=
let β¨_β© := nonempty_fintype ΞΉ
map_exp (Pi.evalRingHom πΈ i) (continuous_apply _) x
theorem _root_.Pi.exp_def {ΞΉ : Type*} {πΈ : ΞΉ β Type*} [Finite ΞΉ] [β i, NormedRing (πΈ i)]
[β i, NormedAlgebra β (πΈ i)] [β i, CompleteSpace (πΈ i)] (x : β i, πΈ i) :
exp x = fun i => exp (x i) :=
funext <| Pi.coe_exp x
theorem _root_.Function.update_exp {ΞΉ : Type*} {πΈ : ΞΉ β Type*} [Finite ΞΉ] [DecidableEq ΞΉ]
[β i, NormedRing (πΈ i)] [β i, NormedAlgebra β (πΈ i)] [β i, CompleteSpace (πΈ i)] (x : β i, πΈ i)
(j : ΞΉ) (xj : πΈ j) :
Function.update (exp x) j (exp xj) = exp (Function.update x j xj) := by
ext i
simp_rw [Pi.exp_def]
exact (Function.apply_update (fun i => exp) x j xj i).symm
end Rat
section DivisionAlgebra
variable {πΈ : Type*} [NormedDivisionRing πΈ] [NormedAlgebra β πΈ]
theorem norm_expSeries_div_summable (x : πΈ) : Summable fun n => β(x ^ n / n ! : πΈ)β :=
norm_expSeries_div_summable_of_mem_ball β x
((expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _)
variable [CompleteSpace πΈ]
theorem expSeries_div_summable (x : πΈ) : Summable fun n => x ^ n / n ! :=
(norm_expSeries_div_summable x).of_norm
theorem expSeries_div_hasSum_exp (x : πΈ) : HasSum (fun n => x ^ n / n !) (exp x) :=
expSeries_div_hasSum_exp_of_mem_ball β x ((expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _)
theorem exp_neg (x : πΈ) : exp (-x) = (exp x)β»ΒΉ :=
exp_neg_of_mem_ball β <| (expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _
theorem exp_zsmul (z : β€) (x : πΈ) : exp (z β’ x) = exp x ^ z := by
obtain β¨n, rfl | rflβ© := z.eq_nat_or_neg
Β· rw [zpow_natCast, natCast_zsmul, exp_nsmul]
Β· rw [zpow_neg, zpow_natCast, neg_smul, exp_neg, natCast_zsmul, exp_nsmul]
theorem exp_conj (y : πΈ) (x : πΈ) (hy : y β 0) : exp (y * x * yβ»ΒΉ) = y * exp x * yβ»ΒΉ :=
exp_units_conj (Units.mk0 y hy) x
theorem exp_conj' (y : πΈ) (x : πΈ) (hy : y β 0) : exp (yβ»ΒΉ * x * y) = yβ»ΒΉ * exp x * y :=
exp_units_conj' (Units.mk0 y hy) x
end DivisionAlgebra
section CommAlgebra
variable {π πΈ : Type*} [NormedCommRing πΈ] [NormedAlgebra β πΈ] [CompleteSpace πΈ]
/-- In a commutative Banach-algebra `πΈ` over `π = β` or `π = β`,
`NormedSpace.exp (x+y) = (NormedSpace.exp x) * (NormedSpace.exp y)`. -/
theorem exp_add {x y : πΈ} : exp (x + y) = exp x * exp y :=
exp_add_of_mem_ball ((expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _)
((expSeries_radius_eq_top β πΈ).symm βΈ edist_lt_top _ _)
/-- A version of `NormedSpace.exp_sum_of_commute` for a commutative Banach-algebra. -/
theorem exp_sum {ΞΉ} (s : Finset ΞΉ) (f : ΞΉ β πΈ) : exp (β i β s, f i) = β i β s, exp (f i) := by
rw [exp_sum_of_commute, Finset.noncommProd_eq_prod]
exact fun i _hi j _hj _ => Commute.all _ _
end CommAlgebra
end Normed
section ScalarTower
variable (π π' πΈ : Type*) [Field π] [Field π'] [Ring πΈ] [Algebra π πΈ] [Algebra π' πΈ]
[TopologicalSpace πΈ] [IsTopologicalRing πΈ]
/-- If a normed ring `πΈ` is a normed algebra over two fields, then they define the same
`expSeries` on `πΈ`. -/
theorem expSeries_eq_expSeries (n : β) (x : πΈ) :
(expSeries π πΈ n fun _ => x) = expSeries π' πΈ n fun _ => x := by
rw [expSeries_apply_eq, expSeries_apply_eq, inv_natCast_smul_eq π π']
set_option backward.isDefEq.respectTransparency false in
/-- A version of `Complex.ofReal_exp` for `NormedSpace.exp` instead of `Complex.exp` -/
@[simp, norm_cast]
theorem ofReal_exp_β_β (r : β) : β(exp r) = exp (r : β) :=
map_exp (algebraMap β β) (continuous_algebraMap _ _) r
@[deprecated (since := "2025-11-13")] alias of_real_exp_β_β := ofReal_exp_β_β
end ScalarTower
end NormedSpace