v0.14.0
Loading...
Searching...
No Matches
Tensor3_times_Tensor2.hpp
Go to the documentation of this file.
1// This file has all of the declarations for expressions like Tensor3*Tensor2
2// and Tensor2*Tensor3, yielding a Tensor3 or Tensor1.
3
4#pragma once
5
6#include "../permute.hpp"
7
8namespace FTensor
9{
10 // A(i,j,k) * B(l,m) double contraction
11 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
12 int Dim3, int Dim4, char i, char j, char k, char l, char m,
13 int DimA, int DimX, int DimY, char a, char x, char y>
15 {
18
19 public:
23 : iterA(Itera), iterB(Iterb)
24 {}
25 typename promote<T, U>::V operator()(const int N1) const
26 {
27 typename promote<T, U>::V result(0);
28
29 for(int xx = 0; xx < DimX; ++xx)
30 for(int yy = 0; yy < DimY; ++yy)
31 {
33 xx, yy)
35 }
36 return result;
37 }
38 };
39
40 // A(i,j,k)*B(j,k)
41 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
42 char i, char j, char k>
45 {
46 using TensorExpr
47 = Tensor3_times_Tensor2_double<A, B, T, U, Dim0, Dim1, Dim2, Dim1, Dim2,
48 i, j, k, j, k, Dim0, Dim1, Dim2, i, j, k>;
50 TensorExpr(a, b));
51 }
52
53 // B(j,k)*A(i,j,k)
54 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
55 char i, char j, char k>
58 {
59 return a * b;
60 }
61
62 // A(i,j,k)*B(k,j)
63 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
64 char i, char j, char k>
67 {
68 using TensorExpr
69 = Tensor3_times_Tensor2_double<A, B, T, U, Dim0, Dim1, Dim2, Dim2, Dim1,
70 i, j, k, k, j, Dim0, Dim1, Dim2, i, j, k>;
72 TensorExpr(a, b));
73 }
74
75 // B(k,j)*A(i,j,k)
76 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
77 char i, char j, char k>
80 {
81 return a * b;
82 }
83
84 // A(i,j,k)*B(i,k)
85 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
86 char i, char j, char k>
89 {
90 using TensorExpr
91 = Tensor3_times_Tensor2_double<A, B, T, U, Dim0, Dim1, Dim2, Dim0, Dim2,
92 i, j, k, i, k, Dim1, Dim0, Dim2, j, i, k>;
94 TensorExpr(a, b));
95 }
96
97 // A(i,j,k)*B(i,k)
98 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
99 char i, char j, char k>
102 {
103 return a * b;
104 }
105
106 // A(i,j,k)*B(k,i)
107 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
108 char i, char j, char k>
111 {
112 using TensorExpr
113 = Tensor3_times_Tensor2_double<A, B, T, U, Dim0, Dim1, Dim2, Dim2, Dim0,
114 i, j, k, k, i, Dim1, Dim0, Dim2, j, i, k>;
116 TensorExpr(a, b));
117 }
118
119 // B(k,i)*A(i,j,k)
120 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
121 char i, char j, char k>
124 {
125 return a * b;
126 }
127
128 // A(i,j,k)*B(i,j)
129 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
130 char i, char j, char k>
133 {
134 using TensorExpr
135 = Tensor3_times_Tensor2_double<A, B, T, U, Dim0, Dim1, Dim2, Dim0, Dim1,
136 i, j, k, i, j, Dim2, Dim0, Dim1, k, i, j>;
138 TensorExpr(a, b));
139 }
140
141 // B(i,j)*A(i,j,k)
142 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
143 char i, char j, char k>
146 {
147 return a * b;
148 }
149
150 // A(i,j,k)*B(j,i)
151 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
152 char i, char j, char k>
155 {
156 using TensorExpr
157 = Tensor3_times_Tensor2_double<A, B, T, U, Dim0, Dim1, Dim2, Dim1, Dim0,
158 i, j, k, j, i, Dim2, Dim0, Dim1, k, i, j>;
160 TensorExpr(a, b));
161 }
162
163 // B(j,i)*A(i,j,k)
164 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
165 char i, char j, char k>
168 {
169 return a * b;
170 }
171
172 /* A(i,j,k)*B(k,l)->Tensor3 */
173
174 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
175 int Dim3, char i, char j, char k, char l>
177 {
180
181 template <int Current_Dim>
182 typename promote<T, U>::V eval(const int N1, const int N2, const int N3,
183 const Number<Current_Dim> &) const
184 {
185 return iterA(N1, N2, Current_Dim - 1) * iterB(Current_Dim - 1, N3)
187 }
188 typename promote<T, U>::V
189 eval(const int N1, const int N2, const int N3, const Number<1> &) const
190 {
191 return iterA(N1, N2, 0) * iterB(0, N3);
192 }
193
194 public:
198 : iterA(a), iterB(b)
199 {}
200 typename promote<T, U>::V
201 operator()(const int N1, const int N2, const int N3) const
202 {
203 return eval(N1, N2, N3, Number<Dim2>());
204 }
205 };
206
207 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
208 int Dim3, char i, char j, char k, char l>
209 Tensor3_Expr<
210 Tensor3_times_Tensor2_2_01<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
211 typename promote<T, U>::V, Dim0, Dim1, Dim3, i, j, l>
214 {
215 using TensorExpr = Tensor3_times_Tensor2_2_01<A, B, T, U, Dim0, Dim1, Dim2,
216 Dim3, i, j, k, l>;
218 Dim3, i, j, l>(TensorExpr(a, b));
219 }
220
221 /* B(k,l)*A(i,j,k)->Tensor3 */
222
223 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
224 int Dim3, char i, char j, char k, char l>
225 Tensor3_Expr<
226 Tensor3_times_Tensor2_2_01<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
227 typename promote<T, U>::V, Dim0, Dim1, Dim3, i, j, l>
230 {
231 using TensorExpr = Tensor3_times_Tensor2_2_01<A, B, T, U, Dim0, Dim1, Dim2,
232 Dim3, i, j, k, l>;
234 Dim3, i, j, l>(TensorExpr(a, b));
235 }
236
237 /* A(i,j,k)*B(l,k)->Tensor3 */
238
239 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
240 int Dim3, char i, char j, char k, char l>
242 {
245
246 template <int Current_Dim>
247 typename promote<T, U>::V eval(const int N1, const int N2, const int N3,
248 const Number<Current_Dim> &) const
249 {
250 return iterA(N1, N2, Current_Dim - 1) * iterB(N3, Current_Dim - 1)
252 }
253 typename promote<T, U>::V
254 eval(const int N1, const int N2, const int N3, const Number<1> &) const
255 {
256 return iterA(N1, N2, 0) * iterB(N3, 0);
257 }
258
259 public:
263 : iterA(a), iterB(b)
264 {}
265 typename promote<T, U>::V
266 operator()(const int N1, const int N2, const int N3) const
267 {
268 return eval(N1, N2, N3, Number<Dim2>());
269 }
270 };
271
272 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
273 int Dim3, char i, char j, char k, char l>
274 Tensor3_Expr<
275 Tensor3_times_Tensor2_2_10<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
276 typename promote<T, U>::V, Dim0, Dim1, Dim3, i, j, l>
279 {
280 using TensorExpr = Tensor3_times_Tensor2_2_10<A, B, T, U, Dim0, Dim1, Dim2,
281 Dim3, i, j, k, l>;
283 Dim3, i, j, l>(TensorExpr(a, b));
284 }
285
286 /* B(l,k)*A(i,j,k)->Tensor3 */
287
288 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
289 int Dim3, char i, char j, char k, char l>
290 Tensor3_Expr<
291 Tensor3_times_Tensor2_2_10<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
292 typename promote<T, U>::V, Dim0, Dim1, Dim3, i, j, l>
295 {
296 using TensorExpr = Tensor3_times_Tensor2_2_10<A, B, T, U, Dim0, Dim1, Dim2,
297 Dim3, i, j, k, l>;
299 Dim3, i, j, l>(TensorExpr(a, b));
300 }
301
302 /* A(i,j,l)*B(j,k)->Tensor3 */
303
304 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
305 int Dim3, char i, char j, char k, char l>
307 {
310
311 template <int Current_Dim>
312 typename promote<T, U>::V eval(const int N1, const int N2, const int N3,
313 const Number<Current_Dim> &) const
314 {
315 return iterA(N1, Current_Dim - 1, N3) * iterB(Current_Dim - 1, N2)
317 }
318 typename promote<T, U>::V
319 eval(const int N1, const int N2, const int N3, const Number<1> &) const
320 {
321 return iterA(N1, 0, N3) * iterB(0, N2);
322 }
323
324 public:
328 : iterA(a), iterB(b)
329 {}
330 typename promote<T, U>::V
331 operator()(const int N1, const int N2, const int N3) const
332 {
333 return eval(N1, N2, N3, Number<Dim1>());
334 }
335 };
336
337 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
338 int Dim3, char i, char j, char k, char l>
339 Tensor3_Expr<
340 Tensor3_times_Tensor2_1_01<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
341 typename promote<T, U>::V, Dim0, Dim2, Dim3, i, k, l>
344 {
345 using TensorExpr = Tensor3_times_Tensor2_1_01<A, B, T, U, Dim0, Dim1, Dim2,
346 Dim3, i, j, k, l>;
348 Dim3, i, k, l>(TensorExpr(a, b));
349 }
350
351 /* B(j,k)*A(i,j,l)->Tensor3 */
352
353 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
354 int Dim3, char i, char j, char k, char l>
355 Tensor3_Expr<
356 Tensor3_times_Tensor2_1_01<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
357 typename promote<T, U>::V, Dim0, Dim2, Dim3, i, k, l>
360 {
361 using TensorExpr = Tensor3_times_Tensor2_1_01<A, B, T, U, Dim0, Dim1, Dim2,
362 Dim3, i, j, k, l>;
364 Dim3, i, k, l>(TensorExpr(a, b));
365 }
366
367 /* A(i,j,l)*B(k,j)->Tensor3 */
368
369 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
370 int Dim3, char i, char j, char k, char l>
372 {
375
376 template <int Current_Dim>
377 typename promote<T, U>::V eval(const int N1, const int N2, const int N3,
378 const Number<Current_Dim> &) const
379 {
380 return iterA(N1, Current_Dim - 1, N3) * iterB(N2, Current_Dim - 1)
382 }
383 typename promote<T, U>::V
384 eval(const int N1, const int N2, const int N3, const Number<1> &) const
385 {
386 return iterA(N1, 0, N3) * iterB(N2, 0);
387 }
388
389 public:
393 : iterA(a), iterB(b)
394 {}
395 typename promote<T, U>::V
396 operator()(const int N1, const int N2, const int N3) const
397 {
398 return eval(N1, N2, N3, Number<Dim1>());
399 }
400 };
401
402 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
403 int Dim3, char i, char j, char k, char l>
404 Tensor3_Expr<
405 Tensor3_times_Tensor2_1_10<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
406 typename promote<T, U>::V, Dim0, Dim2, Dim3, i, k, l>
409 {
410 using TensorExpr = Tensor3_times_Tensor2_1_10<A, B, T, U, Dim0, Dim1, Dim2,
411 Dim3, i, j, k, l>;
413 Dim3, i, k, l>(TensorExpr(a, b));
414 }
415
416 /* B(k,j)*A(i,j,l)->Tensor3 */
417
418 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
419 int Dim3, char i, char j, char k, char l>
420 Tensor3_Expr<
421 Tensor3_times_Tensor2_1_10<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
422 typename promote<T, U>::V, Dim0, Dim2, Dim3, i, k, l>
425 {
426 using TensorExpr = Tensor3_times_Tensor2_1_10<A, B, T, U, Dim0, Dim1, Dim2,
427 Dim3, i, j, k, l>;
429 Dim3, i, k, l>(TensorExpr(a, b));
430 }
431
432 /* A(i,k,l)*B(i,j)->Tensor3 */
433
434 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
435 int Dim3, char i, char j, char k, char l>
437 {
440
441 template <int Current_Dim>
442 typename promote<T, U>::V eval(const int N1, const int N2, const int N3,
443 const Number<Current_Dim> &) const
444 {
445 return iterA(Current_Dim - 1, N2, N3) * iterB(Current_Dim - 1, N1)
447 }
448 typename promote<T, U>::V
449 eval(const int N1, const int N2, const int N3, const Number<1> &) const
450 {
451 return iterA(0, N2, N3) * iterB(0, N1);
452 }
453
454 public:
458 : iterA(a), iterB(b)
459 {}
460 typename promote<T, U>::V
461 operator()(const int N1, const int N2, const int N3) const
462 {
463 return eval(N1, N2, N3, Number<Dim0>());
464 }
465 };
466
467 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
468 int Dim3, char i, char j, char k, char l>
469 Tensor3_Expr<
470 Tensor3_times_Tensor2_0_01<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
471 typename promote<T, U>::V, Dim1, Dim2, Dim3, j, k, l>
474 {
475 using TensorExpr = Tensor3_times_Tensor2_0_01<A, B, T, U, Dim0, Dim1, Dim2,
476 Dim3, i, j, k, l>;
478 Dim3, j, k, l>(TensorExpr(a, b));
479 }
480
481 /* B(i,j)*A(i,k,l)->Tensor3 */
482
483 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
484 int Dim3, char i, char j, char k, char l>
485 Tensor3_Expr<
486 Tensor3_times_Tensor2_0_01<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
487 typename promote<T, U>::V, Dim1, Dim2, Dim3, j, k, l>
490 {
491 using TensorExpr = Tensor3_times_Tensor2_0_01<A, B, T, U, Dim0, Dim1, Dim2,
492 Dim3, i, j, k, l>;
494 Dim3, j, k, l>(TensorExpr(a, b));
495 }
496
497 /* A(i,k,l)*B(j,i)->Tensor3 */
498
499 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
500 int Dim3, char i, char j, char k, char l>
502 {
505
506 template <int Current_Dim>
507 typename promote<T, U>::V eval(const int N1, const int N2, const int N3,
508 const Number<Current_Dim> &) const
509 {
510 return iterA(Current_Dim - 1, N2, N3) * iterB(N1, Current_Dim - 1)
512 }
513 typename promote<T, U>::V
514 eval(const int N1, const int N2, const int N3, const Number<1> &) const
515 {
516 return iterA(0, N2, N3) * iterB(N1, 0);
517 }
518
519 public:
523 : iterA(a), iterB(b)
524 {}
525 typename promote<T, U>::V
526 operator()(const int N1, const int N2, const int N3) const
527 {
528 return eval(N1, N2, N3, Number<Dim0>());
529 }
530 };
531
532 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
533 int Dim3, char i, char j, char k, char l>
534 Tensor3_Expr<
535 Tensor3_times_Tensor2_0_10<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
536 typename promote<T, U>::V, Dim1, Dim2, Dim3, j, k, l>
539 {
540 using TensorExpr = Tensor3_times_Tensor2_0_10<A, B, T, U, Dim0, Dim1, Dim2,
541 Dim3, i, j, k, l>;
543 Dim3, j, k, l>(TensorExpr(a, b));
544 }
545
546 /* B(j,i)*A(i,k,l)->Tensor3 */
547
548 template <class A, class B, class T, class U, int Dim0, int Dim1, int Dim2,
549 int Dim3, char i, char j, char k, char l>
550 Tensor3_Expr<
551 Tensor3_times_Tensor2_0_10<A, B, T, U, Dim0, Dim1, Dim2, Dim3, i, j, k, l>,
552 typename promote<T, U>::V, Dim1, Dim2, Dim3, j, k, l>
555 {
556 using TensorExpr = Tensor3_times_Tensor2_0_10<A, B, T, U, Dim0, Dim1, Dim2,
557 Dim3, i, j, k, l>;
559 Dim3, j, k, l>(TensorExpr(a, b));
560 }
561}
static Number< 2 > N2
static Number< 1 > N1
constexpr double a
promote< T, U >::V operator()(const int N1, const int N2, const int N3) const
Tensor3_times_Tensor2_0_01(const Tensor3_Expr< A, T, Dim0, Dim2, Dim3, i, k, l > &a, const Tensor2_Expr< B, U, Dim0, Dim1, i, j > &b)
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< Current_Dim > &) const
Tensor2_Expr< B, U, Dim0, Dim1, i, j > iterB
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< 1 > &) const
Tensor3_Expr< A, T, Dim0, Dim2, Dim3, i, k, l > iterA
Tensor3_times_Tensor2_0_10(const Tensor3_Expr< A, T, Dim0, Dim2, Dim3, i, k, l > &a, const Tensor2_Expr< B, U, Dim1, Dim0, j, i > &b)
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< Current_Dim > &) const
Tensor2_Expr< B, U, Dim1, Dim0, j, i > iterB
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< 1 > &) const
Tensor3_Expr< A, T, Dim0, Dim2, Dim3, i, k, l > iterA
promote< T, U >::V operator()(const int N1, const int N2, const int N3) const
promote< T, U >::V operator()(const int N1, const int N2, const int N3) const
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< Current_Dim > &) const
Tensor3_times_Tensor2_1_01(const Tensor3_Expr< A, T, Dim0, Dim1, Dim3, i, j, l > &a, const Tensor2_Expr< B, U, Dim1, Dim2, j, k > &b)
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< 1 > &) const
Tensor3_Expr< A, T, Dim0, Dim1, Dim3, i, j, l > iterA
Tensor2_Expr< B, U, Dim1, Dim2, j, k > iterB
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< 1 > &) const
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< Current_Dim > &) const
Tensor2_Expr< B, U, Dim2, Dim1, k, j > iterB
promote< T, U >::V operator()(const int N1, const int N2, const int N3) const
Tensor3_Expr< A, T, Dim0, Dim1, Dim3, i, j, l > iterA
Tensor3_times_Tensor2_1_10(const Tensor3_Expr< A, T, Dim0, Dim1, Dim3, i, j, l > &a, const Tensor2_Expr< B, U, Dim2, Dim1, k, j > &b)
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< Current_Dim > &) const
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< 1 > &) const
promote< T, U >::V operator()(const int N1, const int N2, const int N3) const
Tensor3_Expr< A, T, Dim0, Dim1, Dim2, i, j, k > iterA
Tensor3_times_Tensor2_2_01(const Tensor3_Expr< A, T, Dim0, Dim1, Dim2, i, j, k > &a, const Tensor2_Expr< B, U, Dim2, Dim3, k, l > &b)
Tensor2_Expr< B, U, Dim2, Dim3, k, l > iterB
Tensor2_Expr< B, U, Dim3, Dim2, l, k > iterB
promote< T, U >::V operator()(const int N1, const int N2, const int N3) const
Tensor3_times_Tensor2_2_10(const Tensor3_Expr< A, T, Dim0, Dim1, Dim2, i, j, k > &a, const Tensor2_Expr< B, U, Dim2, Dim3, l, k > &b)
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< Current_Dim > &) const
promote< T, U >::V eval(const int N1, const int N2, const int N3, const Number< 1 > &) const
Tensor3_Expr< A, T, Dim0, Dim1, Dim2, i, j, k > iterA
Tensor3_times_Tensor2_double(const Tensor3_Expr< A, T, Dim0, Dim1, Dim2, i, j, k > &Itera, const Tensor2_Expr< B, U, Dim3, Dim4, l, m > &Iterb)
promote< T, U >::V operator()(const int N1) const
Tensor2_Expr< B, U, Dim3, Dim4, l, m > iterB
Tensor3_Expr< A, T, Dim0, Dim1, Dim2, i, j, k > iterA
FTensor::Index< 'm', SPACE_DIM > m
FTensor::Index< 'i', SPACE_DIM > i
FTensor::Index< 'l', 3 > l
FTensor::Index< 'j', 3 > j
FTensor::Index< 'k', 3 > k
const double T
Tensors class implemented by Walter Landry.
Definition: FTensor.hpp:51
promote< T, U >::V operator*(const Ddg_Expr< A, T, Dim, Dim, i, j, k, l > &a, const Ddg_Expr< B, U, Dim, Dim, i, k, j, l > &b)
constexpr AssemblyType A
U eval(const Tensor2_Expr< B, U, Dim0, Dim1, i, j > &rhs, const int N0, const int N1)
U eval(const Tensor3_Expr< B, U, Dim0, Dim1, Dim2, i, j, k > &rhs, const int N0, const int N1, const int N2)