@@ -35,6 +35,9 @@ points (via the definition of torsors requiring a nonempty type).
35
35
36
36
-/
37
37
38
+ open add_action
39
+ open add_torsor
40
+
38
41
/-- `affine_space` is an abbreviation for `add_torsor` in the case
39
42
where the group is a vector space, or more generally a module, but we
40
43
omit the type classes `[ring k]` and `[module k V]` in the type
@@ -45,9 +48,6 @@ add_torsor V P
45
48
46
49
namespace affine_space
47
50
48
- open add_action
49
- open add_torsor
50
-
51
51
variables (k : Type *) (V : Type *) {P : Type *} [ring k] [add_comm_group V] [module k V]
52
52
variables [S : affine_space k V P]
53
53
include S
@@ -56,16 +56,32 @@ include S
56
56
of points. -/
57
57
def vector_span (s : set P) : submodule k V := submodule.span k (vsub_set V s)
58
58
59
+ /-- The `vsub_set` lies within the `vector_span`. -/
60
+ lemma vsub_set_subset_vector_span (s : set P) : vsub_set V s ⊆ vector_span k V s :=
61
+ submodule.subset_span
62
+
63
+ /-- Each pairwise difference is in the `vector_span`. -/
64
+ lemma vsub_mem_vector_span {s : set P} {p1 p2 : P} (hp1 : p1 ∈ s) (hp2 : p2 ∈ s) :
65
+ p1 -ᵥ p2 ∈ vector_span k V s :=
66
+ begin
67
+ rw ←submodule.mem_coe,
68
+ exact set.mem_of_mem_of_subset (vsub_mem_vsub_set V hp1 hp2)
69
+ (vsub_set_subset_vector_span k V s)
70
+ end
71
+
59
72
/-- The points in the affine span of a (possibly empty) set of
60
- points. Use `affine_span` instead to get an `affine_subspace k V P`,
61
- if the set of points is known to be nonempty. -/
73
+ points. Use `affine_span` instead to get an `affine_subspace k V P`. -/
62
74
def span_points (s : set P) : set P :=
63
75
{p | ∃ p1 ∈ s, ∃ v ∈ (vector_span k V s), p = v +ᵥ p1}
64
76
65
77
/-- A point in a set is in its affine span. -/
66
78
lemma mem_span_points (p : P) (s : set P) : p ∈ s → p ∈ span_points k V s
67
79
| hp := ⟨p, hp, 0 , submodule.zero_mem _, (zero_vadd V p).symm⟩
68
80
81
+ /-- A set is contained in its `span_points`. -/
82
+ lemma subset_span_points (s : set P) : s ⊆ span_points k V s :=
83
+ λ p, mem_span_points k V p s
84
+
69
85
/-- The set of points in the affine span of a nonempty set of points
70
86
is nonempty. -/
71
87
lemma span_points_nonempty_of_nonempty {s : set P} :
@@ -96,19 +112,14 @@ begin
96
112
rw ←neg_one_smul k v2,
97
113
exact (vector_span k V s).smul_mem (-1 : k) hv2 },
98
114
refine (vector_span k V s).add_mem _ hv1v2,
99
- unfold vector_span,
100
- change p1a -ᵥ p2a ∈ submodule.span k (vsub_set V s),
101
- have hp1p2 : p1a -ᵥ p2a ∈ vsub_set V s, { use [p1a, hp1a, p2a, hp2a] },
102
- have hp1p2s : vsub_set V s ⊆ submodule.span k (vsub_set V s) := submodule.subset_span,
103
- apply set.mem_of_mem_of_subset hp1p2 hp1p2s
115
+ exact vsub_mem_vector_span k V hp1a hp2a
104
116
end
105
117
106
118
end affine_space
107
119
108
- namespace finset
120
+ open affine_space
109
121
110
- open add_action
111
- open add_torsor
122
+ namespace finset
112
123
113
124
variables {k : Type *} (V : Type *) {P : Type *} [ring k] [add_comm_group V] [module k V]
114
125
variables [S : affine_space k V P]
@@ -245,8 +256,6 @@ end finset
245
256
246
257
section affine_independent
247
258
248
- open add_torsor
249
-
250
259
variables (k : Type *) (V : Type *) {P : Type *} [ring k] [add_comm_group V] [module k V]
251
260
variables [affine_space k V P] {ι : Type *}
252
261
@@ -314,18 +323,13 @@ end
314
323
315
324
end affine_independent
316
325
317
- open add_torsor affine_space
318
-
319
326
/-- An `affine_subspace k V P` is a subset of an `affine_space k V P`
320
- that has an affine space structure induced by a corresponding subspace
321
- of the `module k V`. -/
327
+ that, if not empty, has an affine space structure induced by a
328
+ corresponding subspace of the `module k V`. -/
322
329
structure affine_subspace (k : Type *) (V : Type *) (P : Type *) [ring k] [add_comm_group V]
323
330
[module k V] [affine_space k V P] :=
324
331
(carrier : set P)
325
- (direction : submodule k V)
326
- (nonempty : carrier.nonempty)
327
- (add : ∀ (p : P) (v : V), p ∈ carrier → v ∈ direction → v +ᵥ p ∈ carrier)
328
- (sub : ∀ (p1 p2 : P), p1 ∈ carrier → p2 ∈ carrier → p1 -ᵥ p2 ∈ direction)
332
+ (smul_vsub_vadd_mem : ∀ (c : k) (p1 p2 p3 ∈ carrier), c • (p1 -ᵥ p2 : V) +ᵥ p3 ∈ carrier)
329
333
330
334
namespace affine_subspace
331
335
@@ -345,16 +349,7 @@ iff.rfl
345
349
/-- The whole affine space as a subspace of itself. -/
346
350
def univ : affine_subspace k V P :=
347
351
{ carrier := set.univ,
348
- direction := submodule.span k set.univ,
349
- nonempty := set.nonempty_iff_univ_nonempty.1 S.nonempty,
350
- add := λ p v hp hv, set.mem_univ _,
351
- sub := begin
352
- intros p1 p2 hp1 hp2,
353
- apply set.mem_bInter,
354
- intros x hx,
355
- rw set.mem_set_of_eq at hx,
356
- exact set.mem_of_mem_of_subset (set.mem_univ _) hx
357
- end }
352
+ smul_vsub_vadd_mem := λ _ _ _ _ _ _ _, set.mem_univ _ }
358
353
359
354
/-- `univ`, coerced to a set, is the whole set of points. -/
360
355
@[simp] lemma univ_coe : (univ k V P : set P) = set.univ :=
@@ -368,30 +363,93 @@ instance : inhabited (affine_subspace k V P) := ⟨univ k V P⟩
368
363
369
364
variables {k V P}
370
365
366
+ /-- The direction of an affine subspace is the submodule spanned by
367
+ the pairwise differences of points. (Except in the case of an empty
368
+ affine subspace, where the direction is the zero submodule, every
369
+ vector in the direction is the difference of two points in the affine
370
+ subspace.) -/
371
+ def direction (s : affine_subspace k V P) : submodule k V := vector_span k V (s : set P)
372
+
373
+ /-- The direction equals the `vector_span`. -/
374
+ lemma direction_eq_vector_span (s : affine_subspace k V P) :
375
+ s.direction = vector_span k V (s : set P) :=
376
+ rfl
377
+
378
+ /-- Alternative definition of the direction when the affine subspace
379
+ is nonempty. This is defined so that the order on submodules (as used
380
+ in the definition of `submodule.span`) can be used in the proof of
381
+ `coe_direction_eq_vsub_set`, and is not intended to be used beyond
382
+ that proof. -/
383
+ def direction_of_nonempty {s : affine_subspace k V P} (h : (s : set P).nonempty) :
384
+ submodule k V :=
385
+ { carrier := vsub_set V (s : set P),
386
+ zero_mem' := begin
387
+ cases h with p hp,
388
+ exact (vsub_self V p) ▸ vsub_mem_vsub_set V hp hp
389
+ end ,
390
+ add_mem' := begin
391
+ intros a b ha hb,
392
+ rcases ha with ⟨p1, hp1, p2, hp2, ha⟩,
393
+ rcases hb with ⟨p3, hp3, p4, hp4, hb⟩,
394
+ rw [ha, hb, ←vadd_vsub_assoc],
395
+ refine vsub_mem_vsub_set V _ hp4,
396
+ convert s.smul_vsub_vadd_mem 1 p1 p2 p3 hp1 hp2 hp3,
397
+ rw one_smul
398
+ end ,
399
+ smul_mem' := begin
400
+ intros c v hv,
401
+ rcases hv with ⟨p1, hp1, p2, hp2, hv⟩,
402
+ rw [hv, ←vadd_vsub V (c • (p1 -ᵥ p2)) p2],
403
+ refine vsub_mem_vsub_set V _ hp2,
404
+ exact s.smul_vsub_vadd_mem c p1 p2 p2 hp1 hp2 hp2
405
+ end }
406
+
407
+ /-- `direction_of_nonempty` gives the same submodule as
408
+ `direction`. -/
409
+ lemma direction_of_nonempty_eq_direction {s : affine_subspace k V P} (h : (s : set P).nonempty) :
410
+ direction_of_nonempty h = s.direction :=
411
+ le_antisymm (vsub_set_subset_vector_span k V s) (submodule.span_le.2 set.subset.rfl)
412
+
413
+ /-- The set of vectors in the direction of a nonempty affine subspace
414
+ is given by `vsub_set`. -/
415
+ lemma coe_direction_eq_vsub_set {s : affine_subspace k V P} (h : (s : set P).nonempty) :
416
+ (s.direction : set V) = vsub_set V (s : set P) :=
417
+ direction_of_nonempty_eq_direction h ▸ rfl
418
+
419
+ /-- A vector is in the direction of a nonempty affine subspace if and
420
+ only if it is the subtraction of two vectors in the subspace. -/
421
+ lemma mem_direction_iff_eq_vsub {s : affine_subspace k V P} (h : (s : set P).nonempty) (v : V) :
422
+ v ∈ s.direction ↔ ∃ p1 ∈ s, ∃ p2 ∈ s, v = p1 -ᵥ p2 :=
423
+ begin
424
+ rw [←submodule.mem_coe, coe_direction_eq_vsub_set h],
425
+ exact iff.rfl
426
+ end
427
+
428
+ /-- Adding a vector in the direction to a point in the subspace
429
+ produces a point in the subspace. -/
430
+ lemma vadd_mem_of_mem_direction {s : affine_subspace k V P} {v : V} (hv : v ∈ s.direction) {p : P}
431
+ (hp : p ∈ s) : v +ᵥ p ∈ s :=
432
+ begin
433
+ rw mem_direction_iff_eq_vsub ⟨p, hp⟩ at hv,
434
+ rcases hv with ⟨p1, hp1, p2, hp2, hv⟩,
435
+ rw hv,
436
+ convert s.smul_vsub_vadd_mem 1 p1 p2 p hp1 hp2 hp,
437
+ rw one_smul
438
+ end
439
+
440
+ /-- Subtracting two points in the subspace produces a vector in the
441
+ direction. -/
442
+ lemma vsub_mem_direction {s : affine_subspace k V P} {p1 p2 : P} (hp1 : p1 ∈ s) (hp2 : p2 ∈ s) :
443
+ (p1 -ᵥ p2) ∈ s.direction :=
444
+ vsub_mem_vector_span k V hp1 hp2
445
+
371
446
/-- Two affine subspaces are equal if they have the same points. -/
372
447
@[ext] lemma ext {s1 s2 : affine_subspace k V P} (h : (s1 : set P) = s2) : s1 = s2 :=
373
448
begin
374
449
cases s1,
375
450
cases s2,
376
- change s1_carrier = s2_carrier at h,
377
451
congr,
378
- { exact h },
379
- { ext v,
380
- split,
381
- { intro hv,
382
- have hm := s1_nonempty.some_mem,
383
- have hvp := s1_add s1_nonempty.some v hm hv,
384
- conv_rhs at hm { rw h },
385
- conv_rhs at hvp { rw h },
386
- rw ←vadd_vsub V v s1_nonempty.some,
387
- exact s2_sub _ _ hvp hm },
388
- { intro hv,
389
- have hm := s2_nonempty.some_mem,
390
- have hvp := s2_add s2_nonempty.some v hm hv,
391
- conv_rhs at hm { rw ←h },
392
- conv_rhs at hvp { rw ←h },
393
- rw ←vadd_vsub V v s2_nonempty.some,
394
- exact s1_sub _ _ hvp hm } }
452
+ exact h
395
453
end
396
454
397
455
/-- Two affine subspaces with the same direction and nonempty
@@ -405,75 +463,102 @@ begin
405
463
split,
406
464
{ intro hp,
407
465
rw ←vsub_vadd V p hn.some,
408
- refine s2.add _ _ hq2 _ ,
466
+ refine vadd_mem_of_mem_direction _ hq2,
409
467
rw ←hd,
410
- exact s1.sub _ _ hp hq1 },
468
+ exact vsub_mem_direction hp hq1 },
411
469
{ intro hp,
412
470
rw ←vsub_vadd V p hn.some,
413
- refine s1.add _ _ hq1 _ ,
471
+ refine vadd_mem_of_mem_direction _ hq1,
414
472
rw hd,
415
- exact s2.sub _ _ hp hq2 }
473
+ exact vsub_mem_direction hp hq2 }
416
474
end
417
475
418
476
/-- Construct an affine subspace from a point and a direction. -/
419
- def mk_of_point_of_direction (p : P) (direction : submodule k V) : affine_subspace k V P :=
477
+ def mk' (p : P) (direction : submodule k V) : affine_subspace k V P :=
420
478
{ carrier := {q | ∃ v ∈ direction, q = v +ᵥ p},
421
- direction := direction,
422
- nonempty := ⟨p, ⟨0 , ⟨direction.zero_mem, (add_action.zero_vadd _ _).symm⟩⟩⟩,
423
- add := λ p2 v hp2 hv, begin
424
- rcases hp2 with ⟨v2, hv2, hp2⟩,
425
- use [v + v2, direction.add_mem hv hv2],
426
- rw [←add_action.vadd_assoc, hp2]
427
- end ,
428
- sub := λ p1 p2 hp1 hp2, begin
479
+ smul_vsub_vadd_mem := λ c p1 p2 p3 hp1 hp2 hp3, begin
429
480
rcases hp1 with ⟨v1, hv1, hp1⟩,
430
481
rcases hp2 with ⟨v2, hv2, hp2⟩,
431
- rw [hp1, hp2, vadd_vsub_vadd_cancel_right],
432
- exact direction.sub_mem hv1 hv2
482
+ rcases hp3 with ⟨v3, hv3, hp3⟩,
483
+ use [c • (v1 - v2) + v3,
484
+ direction.add_mem (direction.smul_mem c (direction.sub_mem hv1 hv2)) hv3],
485
+ simp [hp1, hp2, hp3, vadd_assoc]
433
486
end }
434
487
435
- /-- The direction of an affine space constructed from a point and a
436
- direction. -/
437
- @[simp] lemma direction_mk_of_point_of_direction (p : P) (direction : submodule k V) :
438
- (mk_of_point_of_direction p direction).direction = direction :=
439
- rfl
440
-
441
488
/-- An affine space constructed from a point and a direction contains
442
489
that point. -/
443
- lemma mem_mk_of_point_of_direction (p : P) (direction : submodule k V) :
444
- p ∈ mk_of_point_of_direction p direction :=
490
+ lemma self_mem_mk' (p : P) (direction : submodule k V) :
491
+ p ∈ mk' p direction :=
445
492
⟨0 , ⟨direction.zero_mem, (add_action.zero_vadd _ _).symm⟩⟩
446
493
494
+ /-- An affine space constructed from a point and a direction contains
495
+ the result of adding a vector in that direction to that point. -/
496
+ lemma vadd_mem_mk' {v : V} (p : P) {direction : submodule k V} (hv : v ∈ direction) :
497
+ v +ᵥ p ∈ mk' p direction :=
498
+ ⟨v, hv, rfl⟩
499
+
500
+ /-- An affine space constructed from a point and a direction is
501
+ nonempty. -/
502
+ lemma mk'_nonempty (p : P) (direction : submodule k V) : (mk' p direction : set P).nonempty :=
503
+ ⟨p, self_mem_mk' p direction⟩
504
+
505
+ /-- The direction of an affine space constructed from a point and a
506
+ direction. -/
507
+ @[simp] lemma direction_mk' (p : P) (direction : submodule k V) :
508
+ (mk' p direction).direction = direction :=
509
+ begin
510
+ ext v,
511
+ rw mem_direction_iff_eq_vsub (mk'_nonempty _ _),
512
+ split,
513
+ { rintros ⟨p1, ⟨v1, hv1, hp1⟩, p2, ⟨v2, hv2, hp2⟩, hv⟩,
514
+ rw [hv, hp1, hp2, vadd_vsub_vadd_cancel_right],
515
+ exact direction.sub_mem hv1 hv2 },
516
+ { exact λ hv, ⟨v +ᵥ p, vadd_mem_mk' _ hv, p,
517
+ self_mem_mk' _ _, (vadd_vsub _ _ _).symm⟩ }
518
+ end
519
+
447
520
/-- Constructing an affine subspace from a point in a subspace and
448
521
that subspace's direction yields the original subspace. -/
449
- @[simp] lemma mk_of_point_of_direction_eq {s : affine_subspace k V P} {p : P} (hp : p ∈ s) :
450
- mk_of_point_of_direction p s.direction = s :=
451
- ext_of_direction_eq rfl ⟨p, set.mem_inter (mem_mk_of_point_of_direction _ _) hp⟩
522
+ @[simp] lemma mk'_eq {s : affine_subspace k V P} {p : P} (hp : p ∈ s) : mk' p s.direction = s :=
523
+ ext_of_direction_eq (direction_mk' p s.direction)
524
+ ⟨p, set.mem_inter (self_mem_mk' _ _) hp⟩
452
525
453
526
end affine_subspace
454
527
455
528
section affine_span
456
529
457
- variables (k : Type *) (V : Type *) ( P : Type *) [ring k] [add_comm_group V] [module k V]
530
+ variables (k : Type *) (V : Type *) { P : Type *} [ring k] [add_comm_group V] [module k V]
458
531
[affine_space k V P]
459
532
460
- /-- The affine span of a nonempty set of points is the smallest affine
461
- subspace containing those points. (Actually defined here in terms of
462
- spans in modules.) -/
463
- def affine_span (s : set P) (h : s.nonempty) : affine_subspace k V P :=
533
+ /-- The affine span of a set of points is the smallest affine subspace
534
+ containing those points. (Actually defined here in terms of spans in
535
+ modules.) -/
536
+ def affine_span (s : set P) : affine_subspace k V P :=
464
537
{ carrier := span_points k V s,
465
- direction := vector_span k V s ,
466
- nonempty := span_points_nonempty_of_nonempty k V h,
467
- add := λ p v hp hv, vadd_mem_span_points_of_mem_span_points_of_mem_vector_span k V hp hv,
468
- sub := λ p1 p2 hp1 hp2, vsub_mem_vector_span_of_mem_span_points_of_mem_span_points k V hp1 hp2 }
538
+ smul_vsub_vadd_mem := λ c p1 p2 p3 hp1 hp2 hp3 ,
539
+ vadd_mem_span_points_of_mem_span_points_of_mem_vector_span k V hp3
540
+ ((vector_span k V s).smul_mem c
541
+ ( vsub_mem_vector_span_of_mem_span_points_of_mem_span_points k V hp1 hp2)) }
469
542
470
543
/-- The affine span, converted to a set, is `span_points`. -/
471
- @[simp] lemma affine_span_coe (s : set P) (h : s.nonempty ) :
472
- (affine_span k V P s h : set P) = span_points k V s :=
544
+ @[simp] lemma coe_affine_span (s : set P) :
545
+ (affine_span k V s : set P) = span_points k V s :=
473
546
rfl
474
547
548
+ /-- The direction of the affine span is the `vector_span`. -/
549
+ lemma direction_affine_span (s : set P) : (affine_span k V s).direction = vector_span k V s :=
550
+ begin
551
+ apply le_antisymm,
552
+ { refine submodule.span_le.2 _,
553
+ rintros v ⟨p1, ⟨p2, hp2, v1, hv1, hp1⟩, p3, ⟨p4, hp4, v2, hv2, hp3⟩, hv⟩,
554
+ rw [hv, hp1, hp3, vsub_vadd_eq_vsub_sub, vadd_vsub_assoc, submodule.mem_coe],
555
+ exact (vector_span k V s).sub_mem ((vector_span k V s).add_mem hv1
556
+ (vsub_mem_vector_span k V hp2 hp4)) hv2 },
557
+ { exact submodule.span_mono (vsub_set_mono V (subset_span_points k V s)) }
558
+ end
559
+
475
560
/-- A point in a set is in its affine span. -/
476
- lemma affine_span_mem ( p : P) ( s : set P) (hp : p ∈ s) : p ∈ affine_span k V P s ⟨p, hp⟩ :=
561
+ lemma mem_affine_span { p : P} { s : set P} (hp : p ∈ s) : p ∈ affine_span k V s :=
477
562
mem_span_points k V p s hp
478
563
479
564
end affine_span
0 commit comments