Chris@49
|
1 // Copyright (C) 2009-2013 NICTA (www.nicta.com.au)
|
Chris@49
|
2 // Copyright (C) 2009-2013 Conrad Sanderson
|
Chris@49
|
3 //
|
Chris@49
|
4 // This Source Code Form is subject to the terms of the Mozilla Public
|
Chris@49
|
5 // License, v. 2.0. If a copy of the MPL was not distributed with this
|
Chris@49
|
6 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
Chris@49
|
7
|
Chris@49
|
8
|
Chris@49
|
9 //! \addtogroup glue_mixed
|
Chris@49
|
10 //! @{
|
Chris@49
|
11
|
Chris@49
|
12
|
Chris@49
|
13
|
Chris@49
|
14 //! matrix multiplication with different element types
|
Chris@49
|
15 template<typename T1, typename T2>
|
Chris@49
|
16 inline
|
Chris@49
|
17 void
|
Chris@49
|
18 glue_mixed_times::apply(Mat<typename eT_promoter<T1,T2>::eT>& out, const mtGlue<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_times>& X)
|
Chris@49
|
19 {
|
Chris@49
|
20 arma_extra_debug_sigprint();
|
Chris@49
|
21
|
Chris@49
|
22 typedef typename T1::elem_type eT1;
|
Chris@49
|
23 typedef typename T2::elem_type eT2;
|
Chris@49
|
24
|
Chris@49
|
25 const unwrap_check_mixed<T1> tmp1(X.A, out);
|
Chris@49
|
26 const unwrap_check_mixed<T2> tmp2(X.B, out);
|
Chris@49
|
27
|
Chris@49
|
28 const Mat<eT1>& A = tmp1.M;
|
Chris@49
|
29 const Mat<eT2>& B = tmp2.M;
|
Chris@49
|
30
|
Chris@49
|
31 arma_debug_assert_mul_size(A, B, "matrix multiplication");
|
Chris@49
|
32
|
Chris@49
|
33 out.set_size(A.n_rows, B.n_cols);
|
Chris@49
|
34
|
Chris@49
|
35 gemm_mixed<>::apply(out, A, B);
|
Chris@49
|
36 }
|
Chris@49
|
37
|
Chris@49
|
38
|
Chris@49
|
39
|
Chris@49
|
40 //! matrix addition with different element types
|
Chris@49
|
41 template<typename T1, typename T2>
|
Chris@49
|
42 inline
|
Chris@49
|
43 void
|
Chris@49
|
44 glue_mixed_plus::apply(Mat<typename eT_promoter<T1,T2>::eT>& out, const mtGlue<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_plus>& X)
|
Chris@49
|
45 {
|
Chris@49
|
46 arma_extra_debug_sigprint();
|
Chris@49
|
47
|
Chris@49
|
48 typedef typename T1::elem_type eT1;
|
Chris@49
|
49 typedef typename T2::elem_type eT2;
|
Chris@49
|
50
|
Chris@49
|
51 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
52
|
Chris@49
|
53 promote_type<eT1,eT2>::check();
|
Chris@49
|
54
|
Chris@49
|
55 const Proxy<T1> A(X.A);
|
Chris@49
|
56 const Proxy<T2> B(X.B);
|
Chris@49
|
57
|
Chris@49
|
58 arma_debug_assert_same_size(A, B, "addition");
|
Chris@49
|
59
|
Chris@49
|
60 const uword n_rows = A.get_n_rows();
|
Chris@49
|
61 const uword n_cols = A.get_n_cols();
|
Chris@49
|
62
|
Chris@49
|
63 out.set_size(n_rows, n_cols);
|
Chris@49
|
64
|
Chris@49
|
65 out_eT* out_mem = out.memptr();
|
Chris@49
|
66 const uword n_elem = out.n_elem;
|
Chris@49
|
67
|
Chris@49
|
68 const bool prefer_at_accessor = (Proxy<T1>::prefer_at_accessor || Proxy<T2>::prefer_at_accessor);
|
Chris@49
|
69
|
Chris@49
|
70 if(prefer_at_accessor == false)
|
Chris@49
|
71 {
|
Chris@49
|
72 typename Proxy<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
73 typename Proxy<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
74
|
Chris@49
|
75 if(memory::is_aligned(out_mem))
|
Chris@49
|
76 {
|
Chris@49
|
77 memory::mark_as_aligned(out_mem);
|
Chris@49
|
78
|
Chris@49
|
79 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
80 {
|
Chris@49
|
81 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) + upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
82 }
|
Chris@49
|
83 }
|
Chris@49
|
84 else
|
Chris@49
|
85 {
|
Chris@49
|
86 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
87 {
|
Chris@49
|
88 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) + upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
89 }
|
Chris@49
|
90 }
|
Chris@49
|
91 }
|
Chris@49
|
92 else
|
Chris@49
|
93 {
|
Chris@49
|
94 uword i = 0;
|
Chris@49
|
95
|
Chris@49
|
96 for(uword col=0; col < n_cols; ++col)
|
Chris@49
|
97 for(uword row=0; row < n_rows; ++row)
|
Chris@49
|
98 {
|
Chris@49
|
99 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col)) + upgrade_val<eT1,eT2>::apply(B.at(row,col));
|
Chris@49
|
100 ++i;
|
Chris@49
|
101 }
|
Chris@49
|
102 }
|
Chris@49
|
103 }
|
Chris@49
|
104
|
Chris@49
|
105
|
Chris@49
|
106
|
Chris@49
|
107 //! matrix subtraction with different element types
|
Chris@49
|
108 template<typename T1, typename T2>
|
Chris@49
|
109 inline
|
Chris@49
|
110 void
|
Chris@49
|
111 glue_mixed_minus::apply(Mat<typename eT_promoter<T1,T2>::eT>& out, const mtGlue<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_minus>& X)
|
Chris@49
|
112 {
|
Chris@49
|
113 arma_extra_debug_sigprint();
|
Chris@49
|
114
|
Chris@49
|
115 typedef typename T1::elem_type eT1;
|
Chris@49
|
116 typedef typename T2::elem_type eT2;
|
Chris@49
|
117
|
Chris@49
|
118 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
119
|
Chris@49
|
120 promote_type<eT1,eT2>::check();
|
Chris@49
|
121
|
Chris@49
|
122 const Proxy<T1> A(X.A);
|
Chris@49
|
123 const Proxy<T2> B(X.B);
|
Chris@49
|
124
|
Chris@49
|
125 arma_debug_assert_same_size(A, B, "subtraction");
|
Chris@49
|
126
|
Chris@49
|
127 const uword n_rows = A.get_n_rows();
|
Chris@49
|
128 const uword n_cols = A.get_n_cols();
|
Chris@49
|
129
|
Chris@49
|
130 out.set_size(n_rows, n_cols);
|
Chris@49
|
131
|
Chris@49
|
132 out_eT* out_mem = out.memptr();
|
Chris@49
|
133 const uword n_elem = out.n_elem;
|
Chris@49
|
134
|
Chris@49
|
135 const bool prefer_at_accessor = (Proxy<T1>::prefer_at_accessor || Proxy<T2>::prefer_at_accessor);
|
Chris@49
|
136
|
Chris@49
|
137 if(prefer_at_accessor == false)
|
Chris@49
|
138 {
|
Chris@49
|
139 typename Proxy<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
140 typename Proxy<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
141
|
Chris@49
|
142 if(memory::is_aligned(out_mem))
|
Chris@49
|
143 {
|
Chris@49
|
144 memory::mark_as_aligned(out_mem);
|
Chris@49
|
145
|
Chris@49
|
146 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
147 {
|
Chris@49
|
148 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) - upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
149 }
|
Chris@49
|
150 }
|
Chris@49
|
151 else
|
Chris@49
|
152 {
|
Chris@49
|
153 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
154 {
|
Chris@49
|
155 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) - upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
156 }
|
Chris@49
|
157 }
|
Chris@49
|
158 }
|
Chris@49
|
159 else
|
Chris@49
|
160 {
|
Chris@49
|
161 uword i = 0;
|
Chris@49
|
162
|
Chris@49
|
163 for(uword col=0; col < n_cols; ++col)
|
Chris@49
|
164 for(uword row=0; row < n_rows; ++row)
|
Chris@49
|
165 {
|
Chris@49
|
166 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col)) - upgrade_val<eT1,eT2>::apply(B.at(row,col));
|
Chris@49
|
167 ++i;
|
Chris@49
|
168 }
|
Chris@49
|
169 }
|
Chris@49
|
170 }
|
Chris@49
|
171
|
Chris@49
|
172
|
Chris@49
|
173
|
Chris@49
|
174 //! element-wise matrix division with different element types
|
Chris@49
|
175 template<typename T1, typename T2>
|
Chris@49
|
176 inline
|
Chris@49
|
177 void
|
Chris@49
|
178 glue_mixed_div::apply(Mat<typename eT_promoter<T1,T2>::eT>& out, const mtGlue<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_div>& X)
|
Chris@49
|
179 {
|
Chris@49
|
180 arma_extra_debug_sigprint();
|
Chris@49
|
181
|
Chris@49
|
182 typedef typename T1::elem_type eT1;
|
Chris@49
|
183 typedef typename T2::elem_type eT2;
|
Chris@49
|
184
|
Chris@49
|
185 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
186
|
Chris@49
|
187 promote_type<eT1,eT2>::check();
|
Chris@49
|
188
|
Chris@49
|
189 const Proxy<T1> A(X.A);
|
Chris@49
|
190 const Proxy<T2> B(X.B);
|
Chris@49
|
191
|
Chris@49
|
192 arma_debug_assert_same_size(A, B, "element-wise division");
|
Chris@49
|
193
|
Chris@49
|
194 const uword n_rows = A.get_n_rows();
|
Chris@49
|
195 const uword n_cols = A.get_n_cols();
|
Chris@49
|
196
|
Chris@49
|
197 out.set_size(n_rows, n_cols);
|
Chris@49
|
198
|
Chris@49
|
199 out_eT* out_mem = out.memptr();
|
Chris@49
|
200 const uword n_elem = out.n_elem;
|
Chris@49
|
201
|
Chris@49
|
202 const bool prefer_at_accessor = (Proxy<T1>::prefer_at_accessor || Proxy<T2>::prefer_at_accessor);
|
Chris@49
|
203
|
Chris@49
|
204 if(prefer_at_accessor == false)
|
Chris@49
|
205 {
|
Chris@49
|
206 typename Proxy<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
207 typename Proxy<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
208
|
Chris@49
|
209 if(memory::is_aligned(out_mem))
|
Chris@49
|
210 {
|
Chris@49
|
211 memory::mark_as_aligned(out_mem);
|
Chris@49
|
212
|
Chris@49
|
213 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
214 {
|
Chris@49
|
215 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) / upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
216 }
|
Chris@49
|
217 }
|
Chris@49
|
218 else
|
Chris@49
|
219 {
|
Chris@49
|
220 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
221 {
|
Chris@49
|
222 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) / upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
223 }
|
Chris@49
|
224 }
|
Chris@49
|
225 }
|
Chris@49
|
226 else
|
Chris@49
|
227 {
|
Chris@49
|
228 uword i = 0;
|
Chris@49
|
229
|
Chris@49
|
230 for(uword col=0; col < n_cols; ++col)
|
Chris@49
|
231 for(uword row=0; row < n_rows; ++row)
|
Chris@49
|
232 {
|
Chris@49
|
233 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col)) / upgrade_val<eT1,eT2>::apply(B.at(row,col));
|
Chris@49
|
234 ++i;
|
Chris@49
|
235 }
|
Chris@49
|
236 }
|
Chris@49
|
237 }
|
Chris@49
|
238
|
Chris@49
|
239
|
Chris@49
|
240
|
Chris@49
|
241 //! element-wise matrix multiplication with different element types
|
Chris@49
|
242 template<typename T1, typename T2>
|
Chris@49
|
243 inline
|
Chris@49
|
244 void
|
Chris@49
|
245 glue_mixed_schur::apply(Mat<typename eT_promoter<T1,T2>::eT>& out, const mtGlue<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_schur>& X)
|
Chris@49
|
246 {
|
Chris@49
|
247 arma_extra_debug_sigprint();
|
Chris@49
|
248
|
Chris@49
|
249 typedef typename T1::elem_type eT1;
|
Chris@49
|
250 typedef typename T2::elem_type eT2;
|
Chris@49
|
251
|
Chris@49
|
252 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
253
|
Chris@49
|
254 promote_type<eT1,eT2>::check();
|
Chris@49
|
255
|
Chris@49
|
256 const Proxy<T1> A(X.A);
|
Chris@49
|
257 const Proxy<T2> B(X.B);
|
Chris@49
|
258
|
Chris@49
|
259 arma_debug_assert_same_size(A, B, "element-wise multiplication");
|
Chris@49
|
260
|
Chris@49
|
261 const uword n_rows = A.get_n_rows();
|
Chris@49
|
262 const uword n_cols = A.get_n_cols();
|
Chris@49
|
263
|
Chris@49
|
264 out.set_size(n_rows, n_cols);
|
Chris@49
|
265
|
Chris@49
|
266 out_eT* out_mem = out.memptr();
|
Chris@49
|
267 const uword n_elem = out.n_elem;
|
Chris@49
|
268
|
Chris@49
|
269 const bool prefer_at_accessor = (Proxy<T1>::prefer_at_accessor || Proxy<T2>::prefer_at_accessor);
|
Chris@49
|
270
|
Chris@49
|
271 if(prefer_at_accessor == false)
|
Chris@49
|
272 {
|
Chris@49
|
273 typename Proxy<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
274 typename Proxy<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
275
|
Chris@49
|
276 if(memory::is_aligned(out_mem))
|
Chris@49
|
277 {
|
Chris@49
|
278 memory::mark_as_aligned(out_mem);
|
Chris@49
|
279
|
Chris@49
|
280 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
281 {
|
Chris@49
|
282 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) * upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
283 }
|
Chris@49
|
284 }
|
Chris@49
|
285 else
|
Chris@49
|
286 {
|
Chris@49
|
287 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
288 {
|
Chris@49
|
289 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) * upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
290 }
|
Chris@49
|
291 }
|
Chris@49
|
292 }
|
Chris@49
|
293 else
|
Chris@49
|
294 {
|
Chris@49
|
295 uword i = 0;
|
Chris@49
|
296
|
Chris@49
|
297 for(uword col=0; col < n_cols; ++col)
|
Chris@49
|
298 for(uword row=0; row < n_rows; ++row)
|
Chris@49
|
299 {
|
Chris@49
|
300 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col)) * upgrade_val<eT1,eT2>::apply(B.at(row,col));
|
Chris@49
|
301 ++i;
|
Chris@49
|
302 }
|
Chris@49
|
303 }
|
Chris@49
|
304 }
|
Chris@49
|
305
|
Chris@49
|
306
|
Chris@49
|
307
|
Chris@49
|
308 //
|
Chris@49
|
309 //
|
Chris@49
|
310 //
|
Chris@49
|
311
|
Chris@49
|
312
|
Chris@49
|
313
|
Chris@49
|
314 //! cube addition with different element types
|
Chris@49
|
315 template<typename T1, typename T2>
|
Chris@49
|
316 inline
|
Chris@49
|
317 void
|
Chris@49
|
318 glue_mixed_plus::apply(Cube<typename eT_promoter<T1,T2>::eT>& out, const mtGlueCube<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_plus>& X)
|
Chris@49
|
319 {
|
Chris@49
|
320 arma_extra_debug_sigprint();
|
Chris@49
|
321
|
Chris@49
|
322 typedef typename T1::elem_type eT1;
|
Chris@49
|
323 typedef typename T2::elem_type eT2;
|
Chris@49
|
324
|
Chris@49
|
325 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
326
|
Chris@49
|
327 promote_type<eT1,eT2>::check();
|
Chris@49
|
328
|
Chris@49
|
329 const ProxyCube<T1> A(X.A);
|
Chris@49
|
330 const ProxyCube<T2> B(X.B);
|
Chris@49
|
331
|
Chris@49
|
332 arma_debug_assert_same_size(A, B, "addition");
|
Chris@49
|
333
|
Chris@49
|
334 const uword n_rows = A.get_n_rows();
|
Chris@49
|
335 const uword n_cols = A.get_n_cols();
|
Chris@49
|
336 const uword n_slices = A.get_n_slices();
|
Chris@49
|
337
|
Chris@49
|
338 out.set_size(n_rows, n_cols, n_slices);
|
Chris@49
|
339
|
Chris@49
|
340 out_eT* out_mem = out.memptr();
|
Chris@49
|
341 const uword n_elem = out.n_elem;
|
Chris@49
|
342
|
Chris@49
|
343 const bool prefer_at_accessor = (ProxyCube<T1>::prefer_at_accessor || ProxyCube<T2>::prefer_at_accessor);
|
Chris@49
|
344
|
Chris@49
|
345 if(prefer_at_accessor == false)
|
Chris@49
|
346 {
|
Chris@49
|
347 typename ProxyCube<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
348 typename ProxyCube<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
349
|
Chris@49
|
350 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
351 {
|
Chris@49
|
352 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) + upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
353 }
|
Chris@49
|
354 }
|
Chris@49
|
355 else
|
Chris@49
|
356 {
|
Chris@49
|
357 uword i = 0;
|
Chris@49
|
358
|
Chris@49
|
359 for(uword slice = 0; slice < n_slices; ++slice)
|
Chris@49
|
360 for(uword col = 0; col < n_cols; ++col )
|
Chris@49
|
361 for(uword row = 0; row < n_rows; ++row )
|
Chris@49
|
362 {
|
Chris@49
|
363 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col,slice)) + upgrade_val<eT1,eT2>::apply(B.at(row,col,slice));
|
Chris@49
|
364 ++i;
|
Chris@49
|
365 }
|
Chris@49
|
366 }
|
Chris@49
|
367 }
|
Chris@49
|
368
|
Chris@49
|
369
|
Chris@49
|
370
|
Chris@49
|
371 //! cube subtraction with different element types
|
Chris@49
|
372 template<typename T1, typename T2>
|
Chris@49
|
373 inline
|
Chris@49
|
374 void
|
Chris@49
|
375 glue_mixed_minus::apply(Cube<typename eT_promoter<T1,T2>::eT>& out, const mtGlueCube<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_minus>& X)
|
Chris@49
|
376 {
|
Chris@49
|
377 arma_extra_debug_sigprint();
|
Chris@49
|
378
|
Chris@49
|
379 typedef typename T1::elem_type eT1;
|
Chris@49
|
380 typedef typename T2::elem_type eT2;
|
Chris@49
|
381
|
Chris@49
|
382 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
383
|
Chris@49
|
384 promote_type<eT1,eT2>::check();
|
Chris@49
|
385
|
Chris@49
|
386 const ProxyCube<T1> A(X.A);
|
Chris@49
|
387 const ProxyCube<T2> B(X.B);
|
Chris@49
|
388
|
Chris@49
|
389 arma_debug_assert_same_size(A, B, "subtraction");
|
Chris@49
|
390
|
Chris@49
|
391 const uword n_rows = A.get_n_rows();
|
Chris@49
|
392 const uword n_cols = A.get_n_cols();
|
Chris@49
|
393 const uword n_slices = A.get_n_slices();
|
Chris@49
|
394
|
Chris@49
|
395 out.set_size(n_rows, n_cols, n_slices);
|
Chris@49
|
396
|
Chris@49
|
397 out_eT* out_mem = out.memptr();
|
Chris@49
|
398 const uword n_elem = out.n_elem;
|
Chris@49
|
399
|
Chris@49
|
400 const bool prefer_at_accessor = (ProxyCube<T1>::prefer_at_accessor || ProxyCube<T2>::prefer_at_accessor);
|
Chris@49
|
401
|
Chris@49
|
402 if(prefer_at_accessor == false)
|
Chris@49
|
403 {
|
Chris@49
|
404 typename ProxyCube<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
405 typename ProxyCube<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
406
|
Chris@49
|
407 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
408 {
|
Chris@49
|
409 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) - upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
410 }
|
Chris@49
|
411 }
|
Chris@49
|
412 else
|
Chris@49
|
413 {
|
Chris@49
|
414 uword i = 0;
|
Chris@49
|
415
|
Chris@49
|
416 for(uword slice = 0; slice < n_slices; ++slice)
|
Chris@49
|
417 for(uword col = 0; col < n_cols; ++col )
|
Chris@49
|
418 for(uword row = 0; row < n_rows; ++row )
|
Chris@49
|
419 {
|
Chris@49
|
420 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col,slice)) - upgrade_val<eT1,eT2>::apply(B.at(row,col,slice));
|
Chris@49
|
421 ++i;
|
Chris@49
|
422 }
|
Chris@49
|
423 }
|
Chris@49
|
424 }
|
Chris@49
|
425
|
Chris@49
|
426
|
Chris@49
|
427
|
Chris@49
|
428 //! element-wise cube division with different element types
|
Chris@49
|
429 template<typename T1, typename T2>
|
Chris@49
|
430 inline
|
Chris@49
|
431 void
|
Chris@49
|
432 glue_mixed_div::apply(Cube<typename eT_promoter<T1,T2>::eT>& out, const mtGlueCube<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_div>& X)
|
Chris@49
|
433 {
|
Chris@49
|
434 arma_extra_debug_sigprint();
|
Chris@49
|
435
|
Chris@49
|
436 typedef typename T1::elem_type eT1;
|
Chris@49
|
437 typedef typename T2::elem_type eT2;
|
Chris@49
|
438
|
Chris@49
|
439 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
440
|
Chris@49
|
441 promote_type<eT1,eT2>::check();
|
Chris@49
|
442
|
Chris@49
|
443 const ProxyCube<T1> A(X.A);
|
Chris@49
|
444 const ProxyCube<T2> B(X.B);
|
Chris@49
|
445
|
Chris@49
|
446 arma_debug_assert_same_size(A, B, "element-wise division");
|
Chris@49
|
447
|
Chris@49
|
448 const uword n_rows = A.get_n_rows();
|
Chris@49
|
449 const uword n_cols = A.get_n_cols();
|
Chris@49
|
450 const uword n_slices = A.get_n_slices();
|
Chris@49
|
451
|
Chris@49
|
452 out.set_size(n_rows, n_cols, n_slices);
|
Chris@49
|
453
|
Chris@49
|
454 out_eT* out_mem = out.memptr();
|
Chris@49
|
455 const uword n_elem = out.n_elem;
|
Chris@49
|
456
|
Chris@49
|
457 const bool prefer_at_accessor = (ProxyCube<T1>::prefer_at_accessor || ProxyCube<T2>::prefer_at_accessor);
|
Chris@49
|
458
|
Chris@49
|
459 if(prefer_at_accessor == false)
|
Chris@49
|
460 {
|
Chris@49
|
461 typename ProxyCube<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
462 typename ProxyCube<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
463
|
Chris@49
|
464 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
465 {
|
Chris@49
|
466 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) / upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
467 }
|
Chris@49
|
468 }
|
Chris@49
|
469 else
|
Chris@49
|
470 {
|
Chris@49
|
471 uword i = 0;
|
Chris@49
|
472
|
Chris@49
|
473 for(uword slice = 0; slice < n_slices; ++slice)
|
Chris@49
|
474 for(uword col = 0; col < n_cols; ++col )
|
Chris@49
|
475 for(uword row = 0; row < n_rows; ++row )
|
Chris@49
|
476 {
|
Chris@49
|
477 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col,slice)) / upgrade_val<eT1,eT2>::apply(B.at(row,col,slice));
|
Chris@49
|
478 ++i;
|
Chris@49
|
479 }
|
Chris@49
|
480 }
|
Chris@49
|
481 }
|
Chris@49
|
482
|
Chris@49
|
483
|
Chris@49
|
484
|
Chris@49
|
485 //! element-wise cube multiplication with different element types
|
Chris@49
|
486 template<typename T1, typename T2>
|
Chris@49
|
487 inline
|
Chris@49
|
488 void
|
Chris@49
|
489 glue_mixed_schur::apply(Cube<typename eT_promoter<T1,T2>::eT>& out, const mtGlueCube<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_schur>& X)
|
Chris@49
|
490 {
|
Chris@49
|
491 arma_extra_debug_sigprint();
|
Chris@49
|
492
|
Chris@49
|
493 typedef typename T1::elem_type eT1;
|
Chris@49
|
494 typedef typename T2::elem_type eT2;
|
Chris@49
|
495
|
Chris@49
|
496 typedef typename promote_type<eT1,eT2>::result out_eT;
|
Chris@49
|
497
|
Chris@49
|
498 promote_type<eT1,eT2>::check();
|
Chris@49
|
499
|
Chris@49
|
500 const ProxyCube<T1> A(X.A);
|
Chris@49
|
501 const ProxyCube<T2> B(X.B);
|
Chris@49
|
502
|
Chris@49
|
503 arma_debug_assert_same_size(A, B, "element-wise multiplication");
|
Chris@49
|
504
|
Chris@49
|
505 const uword n_rows = A.get_n_rows();
|
Chris@49
|
506 const uword n_cols = A.get_n_cols();
|
Chris@49
|
507 const uword n_slices = A.get_n_slices();
|
Chris@49
|
508
|
Chris@49
|
509 out.set_size(n_rows, n_cols, n_slices);
|
Chris@49
|
510
|
Chris@49
|
511 out_eT* out_mem = out.memptr();
|
Chris@49
|
512 const uword n_elem = out.n_elem;
|
Chris@49
|
513
|
Chris@49
|
514 const bool prefer_at_accessor = (ProxyCube<T1>::prefer_at_accessor || ProxyCube<T2>::prefer_at_accessor);
|
Chris@49
|
515
|
Chris@49
|
516 if(prefer_at_accessor == false)
|
Chris@49
|
517 {
|
Chris@49
|
518 typename ProxyCube<T1>::ea_type AA = A.get_ea();
|
Chris@49
|
519 typename ProxyCube<T2>::ea_type BB = B.get_ea();
|
Chris@49
|
520
|
Chris@49
|
521 for(uword i=0; i<n_elem; ++i)
|
Chris@49
|
522 {
|
Chris@49
|
523 out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) * upgrade_val<eT1,eT2>::apply(BB[i]);
|
Chris@49
|
524 }
|
Chris@49
|
525 }
|
Chris@49
|
526 else
|
Chris@49
|
527 {
|
Chris@49
|
528 uword i = 0;
|
Chris@49
|
529
|
Chris@49
|
530 for(uword slice = 0; slice < n_slices; ++slice)
|
Chris@49
|
531 for(uword col = 0; col < n_cols; ++col )
|
Chris@49
|
532 for(uword row = 0; row < n_rows; ++row )
|
Chris@49
|
533 {
|
Chris@49
|
534 out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col,slice)) * upgrade_val<eT1,eT2>::apply(B.at(row,col,slice));
|
Chris@49
|
535 ++i;
|
Chris@49
|
536 }
|
Chris@49
|
537 }
|
Chris@49
|
538 }
|
Chris@49
|
539
|
Chris@49
|
540
|
Chris@49
|
541
|
Chris@49
|
542 //! @}
|