@@ -11,6 +11,16 @@ open_locale big_operators
11
11
12
12
/-!
13
13
# Pi instances for algebraic structures
14
+
15
+ ## Implementation notes
16
+
17
+ We don't use `by pi_instance` directly because currently instances generated by this tactic have
18
+ slightly wrong definitions (extra `id`s and `group.mul` instead of `has_mul.mul`). These little
19
+ bugs prevent Lean from applying a `simp` lemma about `pi.has_one` to `1` coming from `pi.group`.
20
+
21
+ ## TODO
22
+
23
+ Properly fix `tactic.pi_instance`.
14
24
-/
15
25
16
26
namespace pi
@@ -19,64 +29,99 @@ variable {I : Type u} -- The indexing type
19
29
variable {f : I → Type v} -- The family of types already equipped with instances
20
30
variables (x y : Π i, f i) (i : I)
21
31
22
- instance has_zero [∀ i, has_zero $ f i] : has_zero (Π i : I, f i) := ⟨λ i, 0 ⟩
23
- @[simp] lemma zero_apply [∀ i, has_zero $ f i] : (0 : Π i, f i) i = 0 := rfl
32
+ @[to_additive] instance has_one [∀ i, has_one $ f i] : has_one (Π i : I, f i) := ⟨λ _, 1 ⟩
33
+ @[simp, to_additive] lemma one_apply [∀ i, has_one $ f i] : (1 : Π i, f i) i = 1 := rfl
34
+
35
+ @[to_additive]
36
+ instance has_mul [∀ i, has_mul $ f i] : has_mul (Π i : I, f i) := ⟨λ f g i, f i * g i⟩
37
+ @[simp, to_additive] lemma mul_apply [∀ i, has_mul $ f i] : (x * y) i = x i * y i := rfl
38
+
39
+ @[to_additive] instance has_inv [∀ i, has_inv $ f i] : has_inv (Π i : I, f i) := ⟨λ f i, (f i)⁻¹⟩
40
+ @[simp, to_additive] lemma inv_apply [∀ i, has_inv $ f i] : x⁻¹ i = (x i)⁻¹ := rfl
41
+
42
+ instance has_scalar {α : Type *} [Π i, has_scalar α $ f i] :
43
+ has_scalar α (Π i : I, f i) :=
44
+ ⟨λ s x, λ i, s • (x i)⟩
45
+
46
+ @[simp] lemma smul_apply {α : Type *} [Π i, has_scalar α $ f i] (s : α) : (s • x) i = s • x i := rfl
47
+
48
+ instance has_scalar' {g : I → Type *} [Π i, has_scalar (f i) (g i)] :
49
+ has_scalar (Π i, f i) (Π i : I, g i) :=
50
+ ⟨λ s x, λ i, (s i) • (x i)⟩
51
+
52
+ @[simp]
53
+ lemma smul_apply' {g : I → Type *} [∀ i, has_scalar (f i) (g i)] (s : Π i, f i) (x : Π i, g i) :
54
+ (s • x) i = s i • x i :=
55
+ rfl
56
+
57
+ @[to_additive add_semigroup]
58
+ instance semigroup [∀ i, semigroup $ f i] : semigroup (Π i : I, f i) :=
59
+ by refine_struct { mul := (*), .. }; tactic.pi_instance_derive_field
24
60
25
- instance has_one [∀ i, has_one $ f i] : has_one (Π i : I, f i) := ⟨λ i, 1 ⟩
26
- @[simp] lemma one_apply [∀ i, has_one $ f i] : (1 : Π i, f i) i = 1 := rfl
61
+ @[to_additive add_comm_semigroup]
62
+ instance comm_semigroup [∀ i, comm_semigroup $ f i] : comm_semigroup (Π i : I, f i) :=
63
+ by refine_struct { mul := (*), .. }; tactic.pi_instance_derive_field
27
64
28
- attribute [to_additive] pi.has_one
29
- attribute [to_additive] pi.one_apply
65
+ @[to_additive add_monoid]
66
+ instance monoid [∀ i, monoid $ f i] : monoid (Π i : I, f i) :=
67
+ by refine_struct { one := (1 : Π i, f i), mul := (*), .. }; tactic.pi_instance_derive_field
30
68
31
- instance has_add [∀ i, has_add $ f i] : has_add (Π i : I, f i) := ⟨λ x y, λ i, x i + y i⟩
32
- @[simp] lemma add_apply [∀ i, has_add $ f i] : (x + y) i = x i + y i := rfl
69
+ @[to_additive add_comm_monoid]
70
+ instance comm_monoid [∀ i, comm_monoid $ f i] : comm_monoid (Π i : I, f i) :=
71
+ by refine_struct { one := (1 : Π i, f i), mul := (*), .. }; tactic.pi_instance_derive_field
33
72
34
- instance has_mul [∀ i, has_mul $ f i] : has_mul (Π i : I, f i) := ⟨λ x y, λ i, x i * y i⟩
35
- @[simp] lemma mul_apply [∀ i, has_mul $ f i] : (x * y) i = x i * y i := rfl
73
+ @[to_additive add_group]
74
+ instance group [∀ i, group $ f i] : group (Π i : I, f i) :=
75
+ by refine_struct { one := (1 : Π i, f i), mul := (*), inv := has_inv.inv, .. };
76
+ tactic.pi_instance_derive_field
36
77
37
- attribute [to_additive] pi.has_mul
38
- attribute [to_additive] pi.mul_apply
78
+ @[to_additive add_comm_group]
79
+ instance comm_group [∀ i, comm_group $ f i] : comm_group (Π i : I, f i) :=
80
+ by refine_struct { one := (1 : Π i, f i), mul := (*), inv := has_inv.inv, .. };
81
+ tactic.pi_instance_derive_field
39
82
40
- instance has_inv [∀ i, has_inv $ f i] : has_inv (Π i : I, f i) := ⟨λ x, λ i, (x i)⁻¹⟩
41
- @[simp] lemma inv_apply [∀ i, has_inv $ f i] : x⁻¹ i = (x i)⁻¹ := rfl
83
+ instance mul_zero_class [Π i, mul_zero_class $ f i] : mul_zero_class (Π i : I, f i) :=
84
+ by refine_struct { zero := ( 0 : Π i, f i), mul : = (*), .. }; tactic.pi_instance_derive_field
42
85
43
- instance has_neg [∀ i, has_neg $ f i] : has_neg (Π i : I, f i) := ⟨λ x, λ i, -(x i)⟩
44
- @[simp] lemma neg_apply [∀ i, has_neg $ f i] : (-x) i = -x i := rfl
86
+ instance distrib [Π i, distrib $ f i] : distrib (Π i : I, f i) :=
87
+ by refine_struct { add := (+), mul := (*), .. }; tactic.pi_instance_derive_field
45
88
46
- attribute [to_additive] pi.has_inv
47
- attribute [to_additive] pi.inv_apply
89
+ instance semiring [∀ i, semiring $ f i] : semiring (Π i : I, f i) :=
90
+ by refine_struct { zero := (0 : Π i, f i), one := 1 , add := (+), mul := (*), .. };
91
+ tactic.pi_instance_derive_field
48
92
49
- instance has_scalar {α : Type *} [∀ i, has_scalar α $ f i] : has_scalar α (Π i : I, f i) := ⟨λ s x, λ i, s • (x i)⟩
50
- @[simp] lemma smul_apply {α : Type *} [∀ i, has_scalar α $ f i] (s : α) : (s • x) i = s • x i := rfl
93
+ instance ring [∀ i, ring $ f i] : ring (Π i : I, f i) :=
94
+ by refine_struct { zero := (0 : Π i, f i), one := 1 , add := (+), mul := (*),
95
+ neg := has_neg.neg, .. }; tactic.pi_instance_derive_field
51
96
52
- instance semigroup [∀ i, semigroup $ f i] : semigroup (Π i : I, f i) := by pi_instance
53
- instance comm_semigroup [∀ i, comm_semigroup $ f i] : comm_semigroup (Π i : I, f i) := by pi_instance
54
- instance monoid [∀ i, monoid $ f i] : monoid (Π i : I, f i) := by pi_instance
55
- instance comm_monoid [∀ i, comm_monoid $ f i] : comm_monoid (Π i : I, f i) := by pi_instance
56
- instance group [∀ i, group $ f i] : group (Π i : I, f i) := by pi_instance
57
- instance comm_group [∀ i, comm_group $ f i] : comm_group (Π i : I, f i) := by pi_instance
58
- instance add_semigroup [∀ i, add_semigroup $ f i] : add_semigroup (Π i : I, f i) := by pi_instance
59
- instance add_comm_semigroup [∀ i, add_comm_semigroup $ f i] : add_comm_semigroup (Π i : I, f i) := by pi_instance
60
- instance add_monoid [∀ i, add_monoid $ f i] : add_monoid (Π i : I, f i) := by pi_instance
61
- instance add_comm_monoid [∀ i, add_comm_monoid $ f i] : add_comm_monoid (Π i : I, f i) := by pi_instance
62
- instance add_group [∀ i, add_group $ f i] : add_group (Π i : I, f i) := by pi_instance
63
- instance add_comm_group [∀ i, add_comm_group $ f i] : add_comm_group (Π i : I, f i) := by pi_instance
64
- instance semiring [∀ i, semiring $ f i] : semiring (Π i : I, f i) := by pi_instance
65
- instance ring [∀ i, ring $ f i] : ring (Π i : I, f i) := by pi_instance
66
- instance comm_ring [∀ i, comm_ring $ f i] : comm_ring (Π i : I, f i) := by pi_instance
97
+ instance comm_ring [∀ i, comm_ring $ f i] : comm_ring (Π i : I, f i) :=
98
+ by refine_struct { zero := (0 : Π i, f i), one := 1 , add := (+), mul := (*),
99
+ neg := has_neg.neg, .. }; tactic.pi_instance_derive_field
67
100
68
- instance mul_action (α) {m : monoid α} [∀ i, mul_action α $ f i] :
101
+ instance mul_action (α) {m : monoid α} [Π i, mul_action α $ f i] :
69
102
@mul_action α (Π i : I, f i) m :=
70
- { smul := λ c f i, c • f i ,
103
+ { smul := (•) ,
71
104
mul_smul := λ r s f, funext $ λ i, mul_smul _ _ _,
72
105
one_smul := λ f, funext $ λ i, one_smul α _ }
73
106
107
+ instance mul_action' {g : I → Type *} {m : Π i, monoid (f i)} [Π i, mul_action (f i) (g i)] :
108
+ @mul_action (Π i, f i) (Π i : I, g i) (@pi.monoid I f m) :=
109
+ { smul := (•),
110
+ mul_smul := λ r s f, funext $ λ i, mul_smul _ _ _,
111
+ one_smul := λ f, funext $ λ i, one_smul _ _ }
112
+
74
113
instance distrib_mul_action (α) {m : monoid α} {n : ∀ i, add_monoid $ f i} [∀ i, distrib_mul_action α $ f i] :
75
114
@distrib_mul_action α (Π i : I, f i) m (@pi.add_monoid I f n) :=
76
115
{ smul_zero := λ c, funext $ λ i, smul_zero _,
77
116
smul_add := λ c f g, funext $ λ i, smul_add _ _ _,
78
117
..pi.mul_action _ }
79
118
119
+ instance distrib_mul_action' {g : I → Type *} {m : Π i, monoid (f i)} {n : Π i, add_monoid $ g i}
120
+ [Π i, distrib_mul_action (f i) (g i)] :
121
+ @distrib_mul_action (Π i, f i) (Π i : I, g i) (@pi.monoid I f m) (@pi.add_monoid I g n) :=
122
+ { smul_add := by { intros, ext x, apply smul_add },
123
+ smul_zero := by { intros, ext x, apply smul_zero } }
124
+
80
125
variables (I f)
81
126
82
127
instance semimodule (α) {r : semiring α} {m : ∀ i, add_comm_monoid $ f i} [∀ i, semimodule α $ f i] :
@@ -87,41 +132,35 @@ instance semimodule (α) {r : semiring α} {m : ∀ i, add_comm_monoid $ f i} [
87
132
88
133
variables {I f}
89
134
135
+ instance semimodule' {g : I → Type *} {r : Π i, semiring (f i)} {m : Π i, add_comm_monoid (g i)}
136
+ [Π i, semimodule (f i) (g i)] :
137
+ semimodule (Π i, f i) (Π i, g i) :=
138
+ { add_smul := by { intros, ext1, apply add_smul },
139
+ zero_smul := by { intros, ext1, apply zero_smul } }
140
+
141
+ @[to_additive add_left_cancel_semigroup]
90
142
instance left_cancel_semigroup [∀ i, left_cancel_semigroup $ f i] :
91
143
left_cancel_semigroup (Π i : I, f i) :=
92
- by pi_instance
93
-
94
- instance add_left_cancel_semigroup [∀ i, add_left_cancel_semigroup $ f i] :
95
- add_left_cancel_semigroup (Π i : I, f i) :=
96
- by pi_instance
144
+ by refine_struct { mul := (*) }; tactic.pi_instance_derive_field
97
145
146
+ @[to_additive add_right_cancel_semigroup]
98
147
instance right_cancel_semigroup [∀ i, right_cancel_semigroup $ f i] :
99
148
right_cancel_semigroup (Π i : I, f i) :=
100
- by pi_instance
101
-
102
- instance add_right_cancel_semigroup [∀ i, add_right_cancel_semigroup $ f i] :
103
- add_right_cancel_semigroup (Π i : I, f i) :=
104
- by pi_instance
105
-
106
- instance ordered_cancel_comm_monoid [∀ i, ordered_cancel_add_comm_monoid $ f i] :
107
- ordered_cancel_add_comm_monoid (Π i : I, f i) :=
108
- by pi_instance
109
-
110
- instance ordered_add_comm_group [∀ i, ordered_add_comm_group $ f i] :
111
- ordered_add_comm_group (Π i : I, f i) :=
112
- { add_le_add_left := λ x y hxy c i, add_le_add_left (hxy i) _,
113
- ..pi.add_comm_group,
149
+ by refine_struct { mul := (*) }; tactic.pi_instance_derive_field
150
+
151
+ @[to_additive ordered_cancel_add_comm_monoid]
152
+ instance ordered_cancel_comm_monoid [∀ i, ordered_cancel_comm_monoid $ f i] :
153
+ ordered_cancel_comm_monoid (Π i : I, f i) :=
154
+ by refine_struct { mul := (*), one := (1 : Π i, f i), le := (≤), lt := (<), .. pi.partial_order };
155
+ tactic.pi_instance_derive_field
156
+
157
+ @[to_additive ordered_add_comm_group]
158
+ instance ordered_comm_group [∀ i, ordered_comm_group $ f i] :
159
+ ordered_comm_group (Π i : I, f i) :=
160
+ { mul_le_mul_left := λ x y hxy c i, mul_le_mul_left' (hxy i),
161
+ ..pi.comm_group,
114
162
..pi.partial_order }
115
163
116
- attribute [to_additive add_semigroup] pi.semigroup
117
- attribute [to_additive add_comm_semigroup] pi.comm_semigroup
118
- attribute [to_additive add_monoid] pi.monoid
119
- attribute [to_additive add_comm_monoid] pi.comm_monoid
120
- attribute [to_additive add_group] pi.group
121
- attribute [to_additive add_comm_group] pi.comm_group
122
- attribute [to_additive add_left_cancel_semigroup] pi.left_cancel_semigroup
123
- attribute [to_additive add_right_cancel_semigroup] pi.right_cancel_semigroup
124
-
125
164
@[simp] lemma sub_apply [∀ i, add_group $ f i] : (x - y) i = x i - y i := rfl
126
165
127
166
@[to_additive]
@@ -309,16 +348,14 @@ section
309
348
variables {f}
310
349
variables [Π i, semiring (f i)]
311
350
312
- -- it is somewhat unfortunate that we can't easily use `add_monoid_hom.functions_ext` here
351
+ -- we need `apply`+`convert` because Lean fails to unify different `add_monoid` instances
352
+ -- on `Π i, f i`
313
353
@[ext]
314
354
lemma ring_hom.functions_ext [fintype I] (G : Type *) [semiring G] (g h : (Π i, f i) →+* G)
315
355
(w : ∀ (i : I) (x : f i), g (single i x) = h (single i x)) : g = h :=
316
356
begin
317
- ext k,
318
- rw [←finset.univ_sum_single k, ring_hom.map_sum, ring_hom.map_sum],
319
- apply finset.sum_congr rfl,
320
- intros,
321
- apply w,
357
+ apply ring_hom.coe_add_monoid_hom_injective,
358
+ convert add_monoid_hom.functions_ext _ _ _ _; assumption
322
359
end
323
360
end
324
361
end
0 commit comments