src/direct_product.rs

branch
dev
changeset 119
cc0c6a8d0933
parent 118
0fabd0b5914c
child 120
07e487685b29
equal deleted inserted replaced
118:0fabd0b5914c 119:cc0c6a8d0933
37 fn from(Pair(a, b): Pair<A, B>) -> (A, B) { 37 fn from(Pair(a, b): Pair<A, B>) -> (A, B) {
38 (a, b) 38 (a, b)
39 } 39 }
40 } 40 }
41 41
42 // macro_rules! impl_scalarop {
43 // (($a : ty, $b : ty), $field : ty, $trait : ident, $fn : ident, $refl:ident) => {
44 // impl_scalarop!(@doit: $field,
45 // $trait, $fn;
46 // maybe_lifetime!($refl, &'l Pair<$a,$b>),
47 // (maybe_lifetime!($refl, &'l $a),
48 // maybe_lifetime!($refl, &'l $b));
49 // $refl);
50 // };
51 // (@doit: $field : ty,
52 // $trait:ident, $fn:ident;
53 // $self:ty, ($aself:ty, $bself:ty);
54 // $refl:ident) => {
55 // // Scalar as Rhs
56 // impl<'l> $trait<$field>
57 // for $self
58 // where $aself: $trait<$field>,
59 // $bself: $trait<$field> {
60 // type Output = Pair<<$aself as $trait<$field>>::Output,
61 // <$bself as $trait<$field>>::Output>;
62 // #[inline]
63 // fn $fn(self, a : $field) -> Self::Output {
64 // Pair(maybe_ref!($refl, self.0).$fn(a),
65 // maybe_ref!($refl, self.1).$fn(a))
66 // }
67 // }
68 // }
69 // }
70 //
71
72 macro_rules! impl_scalarop_gen {
73 ($field : ty, $trait : ident, $fn : ident, $refl:ident) => {
74 impl_scalarop_gen!(@doit: $field,
75 $trait, $fn;
76 maybe_lifetime!($refl, &'l Pair<A,B>),
77 (maybe_lifetime!($refl, &'l A),
78 maybe_lifetime!($refl, &'l B));
79 $refl);
80 };
81 (@doit: $field : ty,
82 $trait:ident, $fn:ident;
83 $self:ty, ($aself:ty, $bself:ty);
84 $refl:ident) => {
85 // Scalar as Rhs
86 impl<'l, A, B> $trait<$field>
87 for $self
88 where $aself: $trait<$field>,
89 $bself: $trait<$field> {
90 type Output = Pair<<$aself as $trait<$field>>::Output,
91 <$bself as $trait<$field>>::Output>;
92 #[inline]
93 fn $fn(self, a : $field) -> Self::Output {
94 Pair(maybe_ref!($refl, self.0).$fn(a),
95 maybe_ref!($refl, self.1).$fn(a))
96 }
97 }
98 }
99 }
100
101 // Not used due to compiler overflow
102 #[allow(unused_macros)]
103 macro_rules! impl_scalarlhs_op {
104 (($a : ty, $b : ty), $field : ty, $trait:ident, $fn:ident, $refr:ident) => {
105 impl_scalarlhs_op!(@doit: $trait, $fn,
106 maybe_lifetime!($refr, &'r Pair<$a,$b>),
107 (maybe_lifetime!($refr, &'r $a),
108 maybe_lifetime!($refr, &'r $b));
109 $refr, $field);
110 };
111 (@doit: $trait:ident, $fn:ident,
112 $in:ty, ($ain:ty, $bin:ty);
113 $refr:ident, $field:ty) => {
114 impl<'r> $trait<$in>
115 for $field
116 where $field : $trait<$ain>
117 + $trait<$bin> {
118 type Output = Pair<<$field as $trait<$ain>>::Output,
119 <$field as $trait<$bin>>::Output>;
120 #[inline]
121 fn $fn(self, x : $in) -> Self::Output {
122 Pair(self.$fn(maybe_ref!($refr, x.0)),
123 self.$fn(maybe_ref!($refr, x.1)))
124 }
125 }
126 };
127 }
128
129 macro_rules! impl_scalar_assignop {
130 (($a : ty, $b : ty), $field : ty, $trait : ident, $fn : ident) => {
131 impl<'r> $trait<$field> for Pair<$a, $b>
132 where
133 $a: $trait<$field>,
134 $b: $trait<$field>,
135 {
136 #[inline]
137 fn $fn(&mut self, a: $field) -> () {
138 self.0.$fn(a);
139 self.1.$fn(a);
140 }
141 }
142 };
143 }
144
145 macro_rules! impl_unary { 42 macro_rules! impl_unary {
146 ($trait:ident, $fn:ident) => { 43 ($trait:ident, $fn:ident) => {
147 impl<A, B> $trait for Pair<A, B> 44 impl<A, B> $trait for Pair<A, B>
148 where 45 where
149 A: $trait, 46 A: $trait,
225 } 122 }
226 123
227 impl_binary!(Add, add); 124 impl_binary!(Add, add);
228 impl_binary!(Sub, sub); 125 impl_binary!(Sub, sub);
229 126
127 macro_rules! impl_scalar {
128 ($trait:ident, $fn:ident, $F:ty) => {
129 impl<A, B> $trait<$F> for Pair<A, B>
130 where
131 A: $trait<$F>,
132 B: $trait<$F>,
133 {
134 type Output = Pair<A::Output, B::Output>;
135 fn $fn(self, t: $F) -> Self::Output {
136 let Pair(a, b) = self;
137 Pair(a.$fn(t), b.$fn(t))
138 }
139 }
140
141 impl<'a, A, B> $trait<$F> for &'a Pair<A, B>
142 where
143 &'a A: $trait<$F>,
144 &'a B: $trait<$F>,
145 {
146 type Output = Pair<<&'a A as $trait<$F>>::Output, <&'a B as $trait<$F>>::Output>;
147 fn $fn(self, t: $F) -> Self::Output {
148 let Pair(ref a, ref b) = self;
149 Pair(a.$fn(t), b.$fn(t))
150 }
151 }
152
153 // impl<'a, 'b, A, B> $trait<&'b $F> for &'a Pair<A, B>
154 // where
155 // &'a A: $trait<&'b $F>,
156 // &'a B: $trait<&'b $F>,
157 // {
158 // type Output =
159 // Pair<<&'a A as $trait<&'b $F>>::Output, <&'a B as $trait<&'b $F>>::Output>;
160 // fn $fn(self, t: &'b $F) -> Self::Output {
161 // let Pair(ref a, ref b) = self;
162 // Pair(a.$fn(t), b.$fn(t))
163 // }
164 // }
165
166 // impl<'b, A, B> $trait<&'b $F> for Pair<A, B>
167 // where
168 // A: $trait<&'b $F>,
169 // B: $trait<&'b $F>,
170 // {
171 // type Output = Pair<<A as $trait<&'b $F>>::Output, <B as $trait<&'b $F>>::Output>;
172 // fn $fn(self, t: &'b $F) -> Self::Output {
173 // let Pair(a, b) = self;
174 // Pair(a.$fn(t), b.$fn(t))
175 // }
176 // }
177 };
178 }
179
180 impl_scalar!(Mul, mul, f32);
181 impl_scalar!(Mul, mul, f64);
182 impl_scalar!(Sub, sub, f32);
183 impl_scalar!(Sub, sub, f64);
184
185 macro_rules! impl_scalar_lhs {
186 ($trait:ident, $fn:ident, $F:ty) => {
187 impl<A, B> $trait<Pair<A, B>> for $F
188 where
189 $F: $trait<A> + $trait<B>,
190 {
191 type Output = Pair<<$F as $trait<A>>::Output, <$F as $trait<B>>::Output>;
192 fn $fn(self, Pair(a, b): Pair<A, B>) -> Self::Output {
193 Pair(self.$fn(a), self.$fn(b))
194 }
195 }
196
197 // Compiler overflow:
198 //
199 // impl<'a, A, B> $trait<&'a Pair<A, B>> for $F
200 // where
201 // $F: $trait<&'a A> + $trait<&'a B>,
202 // {
203 // type Output = Pair<<$F as $trait<&'a A>>::Output, <$F as $trait<&'a B>>::Output>;
204 // fn $fn(self, Pair(a, b): &'a Pair<A, B>) -> Self::Output {
205 // Pair(self.$fn(a), self.$fn(b))
206 // }
207 // }
208 };
209 }
210
211 impl_scalar_lhs!(Mul, mul, f32);
212 impl_scalar_lhs!(Mul, mul, f64);
213
230 macro_rules! impl_binary_mut { 214 macro_rules! impl_binary_mut {
231 ($trait:ident, $fn:ident) => { 215 ($trait:ident, $fn:ident) => {
232 impl<'a, A, B, C, D> $trait<Pair<C, D>> for Pair<A, B> 216 impl<'a, A, B, C, D> $trait<Pair<C, D>> for Pair<A, B>
233 where 217 where
234 A: $trait<C>, 218 A: $trait<C>,
257 241
258 impl_binary_mut!(AddAssign, add_assign); 242 impl_binary_mut!(AddAssign, add_assign);
259 impl_binary_mut!(SubAssign, sub_assign); 243 impl_binary_mut!(SubAssign, sub_assign);
260 244
261 macro_rules! impl_scalar_mut { 245 macro_rules! impl_scalar_mut {
262 ($trait:ident, $fn:ident) => { 246 ($trait:ident, $fn:ident, $F:ty) => {
263 impl<'a, A, B, F> $trait<F> for Pair<A, B> 247 impl<'a, A, B> $trait<$F> for Pair<A, B>
264 where 248 where
265 A: $trait<F>, 249 A: $trait<$F>,
266 B: $trait<F>, 250 B: $trait<$F>,
267 { 251 {
268 fn $fn(&mut self, t: F) { 252 fn $fn(&mut self, t: $F) {
269 let Pair(ref mut a, ref mut b) = self; 253 let Pair(ref mut a, ref mut b) = self;
270 a.$fn(t); 254 a.$fn(t);
271 b.$fn(t); 255 b.$fn(t);
272 } 256 }
273 } 257 }
274 }; 258 };
275 } 259 }
276 260
277 impl_scalar_mut!(MulAssign, mul_assign); 261 impl_scalar_mut!(MulAssign, mul_assign, f32);
278 impl_scalar_mut!(DivAssign, div_assign); 262 impl_scalar_mut!(MulAssign, mul_assign, f64);
279 263 impl_scalar_mut!(DivAssign, div_assign, f32);
280 #[macro_export] 264 impl_scalar_mut!(DivAssign, div_assign, f64);
281 macro_rules! impl_pair_vectorspace_ops { 265
282 (($a:ty, $b:ty), $field:ty) => { 266 /// We only support 'closed' `Euclidean` `Pair`s, as more general ones cause
283 //impl_pair_vectorspace_ops!(@binary, ($a, $b), Add, add); 267 /// compiler overflows.
284 //impl_pair_vectorspace_ops!(@binary, ($a, $b), Sub, sub);
285 //impl_pair_vectorspace_ops!(@assign, ($a, $b), AddAssign, add_assign);
286 //impl_pair_vectorspace_ops!(@assign, ($a, $b), SubAssign, sub_assign);
287 // impl_pair_vectorspace_ops!(@scalar, ($a, $b), $field, Mul, mul);
288 // impl_pair_vectorspace_ops!(@scalar, ($a, $b), $field, Div, div);
289 // Compiler overflow
290 // $(
291 // impl_pair_vectorspace_ops!(@scalar_lhs, ($a, $b), $field, $impl_scalarlhs_op, Mul, mul);
292 // )*
293 };
294 (@scalar, ($a : ty, $b : ty), $field : ty, $trait : ident, $fn :ident) => {
295 impl_scalarop!(($a, $b), $field, $trait, $fn, ref);
296 impl_scalarop!(($a, $b), $field, $trait, $fn, noref);
297 };
298 (@scalar_lhs, ($a : ty, $b : ty), $field : ty, $trait : ident, $fn : ident) => {
299 impl_scalarlhs_op!(($a, $b), $field, $trait, $fn, ref);
300 impl_scalarlhs_op!(($a, $b), $field, $trait, $fn, noref);
301 };
302 (@scalar_assign, ($a : ty, $b : ty), $field : ty, $trait : ident, $fn : ident) => {
303 impl_scalar_assignop!(($a, $b), $field, $trait, $fn);
304 };
305 }
306
307 // TODO: add what we can here.
308 #[macro_export]
309 macro_rules! impl_pair_vectorspace_ops_gen {
310 ($field:ty) => {
311 // impl_pair_vectorspace_ops_gen!(@binary, Add, add);
312 // impl_pair_vectorspace_ops_gen!(@binary, Sub, sub);
313 // impl_pair_vectorspace_ops_gen!(@assign, AddAssign, add_assign);
314 // impl_pair_vectorspace_ops_gen!(@assign, SubAssign, sub_assign);
315 impl_pair_vectorspace_ops_gen!(@scalar, $field, Mul, mul);
316 impl_pair_vectorspace_ops_gen!(@scalar, $field, Div, div);
317 // impl_pair_vectorspace_ops_gen!(@scalar_assign, $field, MulAssign, mul_assign);
318 // impl_pair_vectorspace_ops_gen!(@scalar_assign, $field, DivAssign, div_assign);
319 };
320 (@scalar, $field : ty, $trait : ident, $fn :ident) => {
321 impl_scalarop_gen!($field, $trait, $fn, ref);
322 impl_scalarop_gen!($field, $trait, $fn, noref);
323 };
324 // (@scalar_lhs, $field : ty, $trait : ident, $fn : ident) => {
325 // impl_scalarlhs_op_gen!(($a, $b), $field, $trait, $fn, ref);
326 // impl_scalarlhs_op_gen!(($a, $b), $field, $trait, $fn, noref);
327 // };
328 // (@scalar_assign, $field : ty, $trait : ident, $fn : ident) => {
329 // impl_scalar_assignop_gen!(($a, $b), $field, $trait, $fn);
330 // };
331 }
332
333 impl_pair_vectorspace_ops_gen!(f32);
334 impl_pair_vectorspace_ops_gen!(f64);
335
336 //impl_pair_vectorspace_ops!((f32, f32), f32);
337 //impl_pair_vectorspace_ops!((f64, f64), f64);
338
339 /// We need to restrict `A` and `B` as [`Euclidean`] to have closed `Output`
340
341 impl<A, B, F: Float> Euclidean<F> for Pair<A, B> 268 impl<A, B, F: Float> Euclidean<F> for Pair<A, B>
342 where 269 where
343 A: Euclidean<F>, 270 A: Euclidean<F>,
344 B: Euclidean<F>, 271 B: Euclidean<F>,
345 //Pair<A, B>: Euclidean<F>, 272 //Pair<A, B>: Euclidean<F>,

mercurial