Arcane  v3.14.10.0
Documentation développeur
Chargement...
Recherche...
Aucune correspondance
TestNumArray.cc
1// -*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
2//-----------------------------------------------------------------------------
3// Copyright 2000-2024 CEA (www.cea.fr) IFPEN (www.ifpenergiesnouvelles.com)
4// See the top-level COPYRIGHT file for details.
5// SPDX-License-Identifier: Apache-2.0
6//-----------------------------------------------------------------------------
7
8#include <gtest/gtest.h>
9
10#include "arcane/utils/NumArray.h"
11
12#include "arcane/utils/Real2.h"
13#include "arcane/utils/Real3.h"
14#include "arcane/utils/Real2x2.h"
15#include "arcane/utils/Real3x3.h"
16
17#include "arcane/utils/NumArrayUtils.h"
18
19#include <vector>
20
21/*---------------------------------------------------------------------------*/
22/*---------------------------------------------------------------------------*/
23
24using namespace Arcane;
25
26/*---------------------------------------------------------------------------*/
27/*---------------------------------------------------------------------------*/
28
29using namespace Arcane;
30
31TEST(NumArray, Basic)
32{
33 std::cout << "TEST_NUMARRAY Basic\n";
34
36 array1(1) = 5.0;
37 ASSERT_EQ(array1(1), 5.0);
38 std::cout << " V=" << array1(1) << "\n";
39 array1[2] = 3.0;
40 ASSERT_EQ(array1[2], 3.0);
41 std::cout << " V=" << array1(1) << "\n";
42 array1.resize(7);
43 ASSERT_EQ(array1.totalNbElement(), 7);
44
46 array2(1, 2) = 5.0;
47 std::cout << " V=" << array2(1, 2) << "\n";
48 array2.resize(7, 5);
49 ASSERT_EQ(array2.totalNbElement(), (7 * 5));
50
52 array3(1, 2, 3) = 5.0;
53 std::cout << " V=" << array3(1, 2, 3) << "\n";
54 ASSERT_EQ(array3(1, 2, 3), 5.0);
55 array3.resize(12, 4, 6);
56 ASSERT_EQ(array3.totalNbElement(), (12 * 4 * 6));
57 array3.fill(0.0);
58 array3(1, 2, 3) = 4.0;
59 array3(2, 3, 5) = 1.0;
60
61 {
63 ASSERT_EQ(array3.extent0(), span_array3.extent0());
64
66 ASSERT_EQ(const_span_array3.to1DSpan(), span_array3.to1DSpan());
67
68 ASSERT_EQ(array3.extent0(), span_array3.extent0());
69 std::cout << "Array3: extents=" << array3.extent0()
70 << "," << array3.extent1() << "," << array3.extent2() << "\n";
71 for (Int32 i = 0; i < array3.extent0(); ++i) {
73 ASSERT_EQ(span_array2.extent0(), span_array3.extent1());
74 ASSERT_EQ(span_array2.extent1(), span_array3.extent2());
75 std::cout << " MDDim2 slice i=" << i << " X=" << span_array2.extent0() << " Y=" << span_array2.extent1() << "\n";
76 for (Int32 x = 0, xn = span_array2.extent0(); x < xn; ++x) {
77 for (Int32 y = 0, yn = span_array2.extent1(); y < yn; ++y) {
78 ASSERT_EQ(span_array2.ptrAt(x, y), span_array3.ptrAt(i, x, y));
79 }
80 }
81 }
82 }
83 {
85 std::cout << "Array2: extents=" << array2.extent0() << "," << array2.extent1() << "\n";
86 for (Int32 i = 0; i < array2.extent0(); ++i) {
87 MDSpan<Real, MDDim1> span_array1 = array2.mdspan().slice(i);
88 ASSERT_EQ(span_array1.extent0(), span_array2.extent1());
89 std::cout << " MDDim1 slice i=" << i << " X=" << span_array2.extent0() << "\n";
90 for (Int32 x = 0, xn = span_array1.extent0(); x < xn; ++x) {
91 ASSERT_EQ(span_array1.ptrAt(x), span_array2.ptrAt(i, x));
92 }
93 }
94 }
96 array4(1, 2, 3, 4) = 5.0;
97 std::cout << " V=" << array4(1, 2, 3, 4) << "\n";
98 array4.resize(8, 3, 7, 5);
99 ASSERT_EQ(array4.totalNbElement(), (8 * 3 * 7 * 5));
100
101 NumArray<Real, MDDim1> num_data1(4, { 2.4, 5.6, 3.3, 5.4 });
102 ASSERT_EQ(num_data1[0], 2.4);
103 ASSERT_EQ(num_data1[1], 5.6);
104 ASSERT_EQ(num_data1[2], 3.3);
105 ASSERT_EQ(num_data1[3], 5.4);
106
107 NumArray<Real, MDDim2, RightLayout> num_data2(3, 2, { 1.4, 15.6, 33.3, 7.4, 4.2, 6.5 });
108 ASSERT_EQ(num_data2(0, 0), 1.4);
109 ASSERT_EQ(num_data2(0, 1), 15.6);
110 ASSERT_EQ(num_data2(1, 0), 33.3);
111 ASSERT_EQ(num_data2(1, 1), 7.4);
112 ASSERT_EQ(num_data2(2, 0), 4.2);
113 ASSERT_EQ(num_data2(2, 1), 6.5);
114}
115
116/*---------------------------------------------------------------------------*/
117/*---------------------------------------------------------------------------*/
118
119TEST(NumArray,Basic2)
120{
121 std::cout << "TEST_NUMARRAY Basic2\n";
122
124 array1.resize(2);
125 array1(1) = 5.0;
126 std::cout << " V=" << array1(1) << "\n";
127
129 array2.resize(2,3);
130 array2(1,2) = 5.0;
131 std::cout << " V=" << array2(1,2) << "\n";
132
134 array3.resize(2,3,4);
135 array3(1,2,3) = 5.0;
136 std::cout << " V=" << array3(1,2,3) << "\n";
137
139 array4.resize(2,3,4,5);
140 array4(1,2,3,4) = 5.0;
141 std::cout << " V=" << array4(1,2,3,4) << "\n";
142}
143
144/*---------------------------------------------------------------------------*/
145/*---------------------------------------------------------------------------*/
146
147TEST(NumArray, Extents)
148{
149 std::cout << "TEST_NUMARRAY Extents\n";
150
156 ASSERT_EQ(1, MDDim1::nb_dynamic);
157 ASSERT_EQ(2, MDDim2::nb_dynamic);
158 ASSERT_EQ(3, MDDim3::nb_dynamic);
159 ;
160 ASSERT_EQ(4, MDDim4::nb_dynamic);
161
162 {
164 x1.resize({ 6, 7 });
165 ASSERT_EQ(x1.extent0(), 2);
166 ASSERT_EQ(x1.extent1(), 6);
167 ASSERT_EQ(x1.extent2(), 3);
168 ASSERT_EQ(x1.extent3(), 7);
169 }
170 {
172 x1.resize(6);
173 ASSERT_EQ(x1.extent0(), 2);
174 ASSERT_EQ(x1.extent1(), 3);
175 ASSERT_EQ(x1.extent2(), 6);
176 }
177}
178
179/*---------------------------------------------------------------------------*/
180/*---------------------------------------------------------------------------*/
181
182TEST(NumArray3,Misc)
183{
184 constexpr int nb_x = 3;
185 constexpr int nb_y = 4;
186 constexpr int nb_z = 5;
187
189 v.fill(0);
190 // Attention, v.extents() change si 'v' est redimensionné
191 auto v_extents = v.extentsWithOffset();
192 {
193 for( Int32 x=0, xn=v.dim1Size(); x<xn; ++x ){
194 for( Int32 y=0, yn=v.dim2Size(); y<yn; ++y ){
195 for( Int32 z=0, zn=v.dim3Size(); z<zn; ++z ){
196 ArrayIndex<3> idx{x,y,z};
197 Int64 offset = v_extents.offset(idx);
198 v(x,y,z) = offset;
199 v({x,y,z}) = offset;
200 v(idx) = offset;
201 }
202 }
203 }
204 }
205 std::cout << "CAPACITY V1=" << v.capacity() << "\n";
206 v.resize(4,5,6);
207 std::cout << "CAPACITY V2=" << v.capacity() << "\n";
208 v.resize(2,7,9);
209 std::cout << "CAPACITY V3=" << v.capacity() << "\n";
210 v.resize(3,2,6);
211 std::cout << "CAPACITY V4=" << v.capacity() << "\n";
212
213 // NOTE: désactive temporairement le test tant que la méthode
214 // resize() de 'NumArray' ne conserve pas les valeurs
215#if NUMARRAY_HAS_VALID_RESIZE
216 // Les valeurs ci-dessous dépendent de l'implémentation actuelle
217 // de NumArray::resize(). Je ne suis pas sur qu'il soit valide de les
218 // tester
219 std::vector<Int64> valid_values =
220 {
221 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11,
222 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
223 24 , 25, 26, 27, 28, 29, 20 , 21, 22, 23, 24, 25
224 };
225 ASSERT_EQ(valid_values.size(),(size_t)36);
226
227 v_extents = v.extentsWithOffset();
228 Int64 index = 0;
229 for( Int64 x=0, xn=v.dim1Size(); x<xn; ++x ){
230 for( Int64 y=0, yn=v.dim2Size(); y<yn; ++y ){
231 for( Int64 z=0, zn=v.dim3Size(); z<zn; ++z ){
232 ArrayBoundsIndex<3> idx{x,y,z};
233 Int64 offset = v_extents.offset(idx);
234 Int64 val1 = v(x,y,z);
235 Int64 val2 = v({x,y,z});
236 std::cout << "XYZ=" << x << " " << y << " " << z
237 << " V=" << val1 << " offset=" << offset << "\n";
238 ASSERT_EQ(index,offset);
240 ASSERT_EQ(valid_values.at(offset),val1);
241 ++index;
242 }
243 }
244 }
245#endif
246}
247
248/*---------------------------------------------------------------------------*/
249/*---------------------------------------------------------------------------*/
250
251namespace
252{
254{
255 std::cout << "IN_CREATE_1\n";
256 NumArray<int,MDDim1> a(size);
257 std::cout << "IN_CREATE_2\n";
258 for(Int32 i=0; i<size; ++i )
259 a(i) = size+i+2;
260 return a;
261}
262}
263TEST(NumArray3, Copy)
264{
265 int nb_x = 3;
266 int nb_y = 4;
267 int nb_z = 5;
269 v.fill(3.2);
270 NumArray<Real, MDDim3> v2(nb_x * 2, nb_y / 2, nb_z * 3);
271
272 v.copy(v2.mdspan());
273
274 {
275 NumArray<int, MDDim1> vi0(4, { 1, 3, 5, 7 });
278 vi2 = vi1;
279 ASSERT_EQ(vi1.to1DSpan(), vi0.to1DSpan());
280 ASSERT_EQ(vi2.to1DSpan(), vi1.to1DSpan());
281 NumArray<int, MDDim1> vi3(vi0.to1DSpan());
282 ASSERT_EQ(vi3.to1DSpan(), vi0.to1DSpan());
283
284 Span<const int> vi0_span(vi0.to1DSmallSpan());
285 Span<const int> vi1_span(vi1.to1DSmallSpan());
286 ASSERT_EQ(vi0.to1DSpan(), vi0_span);
287 ASSERT_EQ(vi1_span, vi1.to1DSpan());
288 ASSERT_EQ(vi1.to1DSmallSpan(), vi0.to1DSmallSpan());
289 ASSERT_EQ(vi1.to1DConstSmallSpan(), vi0.to1DConstSmallSpan());
291 Span<const int> vi1_ref_span(v1_ref.to1DSmallSpan());
292 ASSERT_EQ(vi1_ref_span, vi1.to1DSpan());
293 }
294
295 {
296 NumArray<int, MDDim1> vi0(4, { 1, 3, 5, 7 });
299 vi2 = vi1;
300 ASSERT_EQ(vi1.to1DSpan(), vi0.to1DSpan());
301 ASSERT_EQ(vi2.to1DSpan(), vi1.to1DSpan());
302 }
303}
304
305TEST(NumArray3,Move)
306{
307 // Test NumArray::NumArray(NumArray&&)
308 {
309 std::cout << "PART_1\n";
311 test_move.fill(3);
312 Int32 wanted_size1 = 23;
314 std::cout << "PART_2\n";
315 ASSERT_EQ(test_move.totalNbElement(),wanted_size1) << "Bad size (test move 1)";
316 ASSERT_EQ(test_move[6],wanted_size1+8) << "Bad size (test move 2)";
317 Int32 wanted_size2 = 17;
319 std::cout << "PART_3\n";
320 ASSERT_EQ(test_move.totalNbElement(),wanted_size2) << "Bad size (test move 3)";
321 ASSERT_EQ(test_move[3],wanted_size2+5) << "Bad size (test move 4)";
322 }
323 // Test NumArray::operator=(NumArray&&)
324 {
325 Int32 wanted_size1 = 31;
326 std::cout << "PART_4\n";
328 std::cout << "PART_5\n";
329 ASSERT_EQ(test_move.totalNbElement(),wanted_size1) << "Bad size (test move 1)";
330 ASSERT_EQ(test_move[7],wanted_size1+9) << "Bad size (test move 2)";
331 }
332}
333
334/*---------------------------------------------------------------------------*/
335/*---------------------------------------------------------------------------*/
336
337TEST(NumArray3,Index)
338{
339 ArrayIndex<3> index(1,4,2);
340 auto [i, j, k] = index();
341
342 ASSERT_TRUE(i==1);
343 ASSERT_TRUE(j==4);
344 ASSERT_TRUE(k==2);
345}
346
347namespace
348{
349template<typename T>
350void _setNumArray2Values(T& a)
351{
352 for( Int32 i=0; i<a.dim1Size(); ++i ){
353 for( Int32 j=0; j<a.dim2Size(); ++j ){
354 a(i,j) = (i*253) + j;
355 }
356 }
357}
358template<typename T>
359void _setNumArray3Values(T& a)
360{
361 for( Int32 i=0; i<a.dim1Size(); ++i ){
362 for( Int32 j=0; j<a.dim2Size(); ++j ){
363 for( Int32 k=0; k<a.dim3Size(); ++k ){
364 a(i,j,k) = (i*253) + (j*27) + k;
365 }
366 }
367 }
368}
369}
370
371/*---------------------------------------------------------------------------*/
372/*---------------------------------------------------------------------------*/
373
374TEST(NumArray2,Layout)
375{
376 std::cout << "TEST_NUMARRAY2 Layout\n";
377
378 {
380 ASSERT_EQ(a.totalNbElement(),(3*5));
382 auto values = a.to1DSpan();
383 std::cout << "V=" << values << "\n";
384 UniqueArray<Real> ref_value = { 0, 1, 2, 3, 4, 253, 254, 255, 256, 257, 506, 507, 508, 509, 510 };
385 ASSERT_EQ(values.smallView(),ref_value.view());
386 }
387
388 {
390 ASSERT_EQ(a.totalNbElement(),(3*5));
392 auto values = a.to1DSpan();
393 std::cout << "V=" << values << "\n";
394 UniqueArray<Real> ref_value = { 0, 253, 506, 1, 254, 507, 2, 255, 508, 3, 256, 509, 4, 257, 510 };
395 ASSERT_EQ(values.smallView(),ref_value.view());
396 }
397}
398
399/*---------------------------------------------------------------------------*/
400/*---------------------------------------------------------------------------*/
401
402template<typename NumArray3>
403void _checkRightLayoutDim3(NumArray3& a)
404{
405 // Le tableau doit avoir les dimensions (2,3,5);
406 ASSERT_EQ(a.totalNbElement(),(2*3*5));
407 ASSERT_EQ(a.extent0(),2);
408 ASSERT_EQ(a.extent1(),3);
409 ASSERT_EQ(a.extent2(),5);
411 auto values = a.to1DSpan();
412 std::cout << "V=" << values << "\n";
414 {
415 0, 1, 2, 3, 4, 27, 28, 29, 30, 31, 54, 55, 56, 57, 58,
416 253, 254, 255, 256, 257, 280, 281, 282, 283, 284, 307, 308, 309, 310, 311
417 };
418 ASSERT_EQ(values.smallView(),ref_value.view());
419}
420
421template<typename NumArray3>
422void _checkLeftLayoutDim3(NumArray3& a)
423{
424 // Le tableau doit avoir les dimensions (2,3,5);
425 //NumArray<Real,MDDim3,LeftLayout3> a(2,3,5);
426 ASSERT_EQ(a.totalNbElement(),(2*3*5));
428 auto values = a.to1DSpan();
429 std::cout << "V=" << values << "\n";
431 {
432 0, 253, 27, 280, 54, 307, 1, 254, 28, 281, 55, 308, 2, 255, 29,
433 282, 56, 309, 3, 256, 30, 283, 57, 310, 4, 257, 31, 284, 58, 311
434 };
435 ASSERT_EQ(values.smallView(),ref_value.view());
436}
437
438TEST(NumArray3, Layout)
439{
440 std::cout << "TEST_NUMARRAY3 Layout\n";
441
442 {
444 std::cout << "TEST_NUMARRAY3 RightLayout 1\n";
445 _checkRightLayoutDim3(a);
446 }
447 {
449 std::cout << "TEST_NUMARRAY3 RightLayout 2\n";
450 _checkRightLayoutDim3(a);
451 }
452 {
454 std::cout << "TEST_NUMARRAY3 RightLayout 3\n";
455 _checkRightLayoutDim3(a);
456 }
457 {
459 std::cout << "TEST_NUMARRAY3 RightLayout 4\n";
460 _checkRightLayoutDim3(a);
461 }
462 {
464 std::cout << "TEST_NUMARRAY3 RightLayout 5\n";
465 _checkRightLayoutDim3(a);
466 }
467
468 {
470 std::cout << "TEST_NUMARRAY3 LeftLayout 1\n";
471 _checkLeftLayoutDim3(a);
472 }
473 {
475 std::cout << "TEST_NUMARRAY3 LeftLayout 2\n";
476 _checkLeftLayoutDim3(a);
477 }
478 {
480 std::cout << "TEST_NUMARRAY3 LeftLayout 3\n";
481 _checkLeftLayoutDim3(a);
482 }
483 {
485 std::cout << "TEST_NUMARRAY3 LeftLayout 4\n";
486 _checkLeftLayoutDim3(a);
487 }
488 {
490 std::cout << "TEST_NUMARRAY3 LeftLayout 5\n";
491 _checkLeftLayoutDim3(a);
492 }
493}
494
495/*---------------------------------------------------------------------------*/
496/*---------------------------------------------------------------------------*/
497
498TEST(NumArray,RealN)
499{
500 {
502 a(2) = Real2(0.0,3.2);
503 a(3)(1) = 2.0;
504 ASSERT_EQ(a(3).y,2.0);
505 }
506
507 {
509 const Real3 v(0.0,3.2,5.6);
510 a(0) = v;
511 a(4)(1) = 4.0;
512 ASSERT_EQ(a(4).y,4.0);
513 ASSERT_EQ(a(0),v);
514 }
515
516 {
518 const Real2 v0(1.2,1.7);
519 const Real2x2 v(Real2(3.2,5.6), Real2(3.4,1.7));
520 a(0) = v;
521 a(3)(1,0) = v0.x;
522 a(3)(1,1) = v0.y;
523 a(4)(1,0) = 4.0;
524 ASSERT_EQ(a(4).y.x,4.0);
525 ASSERT_EQ(a(0),v);
526 ASSERT_EQ(a(3)(1),v0);
527 }
528
529 {
531 const Real3 v0(1.2,3.4,1.7);
532 const Real3x3 v(Real3(0.0,3.2,5.6), Real3(1.2,3.4,1.7), Real3(9.2,1.4,5.0));
533 a(0) = v;
534 a(3)(1)(0) = v0.x;
535 a(3)(1)(1) = v0.y;
536 a(3)(1)(2) = v0.z;
537 a(4)(1)(2) = 4.0;
538 ASSERT_EQ(a(4).y.z,4.0);
539 ASSERT_EQ(a(0),v);
540 ASSERT_EQ(a(3)(1),v0);
541 }
542}
543
544/*---------------------------------------------------------------------------*/
545/*---------------------------------------------------------------------------*/
546
548{
549 {
550 const char* values1_str = "1 3 -2 \n -7 -5 12 \n 3 9 11\n";
551 NumArray<Int32, MDDim1> ref_value(9, { 1, 3, -2, -7, -5, 12, 3, 9, 11 });
552 std::istringstream istr1(values1_str);
555 ASSERT_EQ(int32_values.extent0(), 9);
556 ASSERT_EQ(int32_values.to1DSpan(), ref_value.to1DSpan());
557 }
558 {
559 const char* values1_str = "1.1 3.3 -2.5 \n \n 2.1 4.99 12.23 \n 23 \n 45.1 11.9e2 -12.6e4\n";
560 NumArray<Real, MDDim1> ref_value(10, { 1.1, 3.3, -2.5, 2.1, 4.99, 12.23, 23, 45.1, 11.9e2, -12.6e4 });
561 std::istringstream istr1(values1_str);
564 ASSERT_EQ(real_values.extent0(), 10);
565 ASSERT_EQ(real_values.to1DSpan(), ref_value.to1DSpan());
566 }
567}
568namespace TestCopyNumArray
569{
570using Real = double;
571
576
577auto bar()
578{
580 tpq.fill(1.526);
581 auto const& w = tpq;
582 std::cout << w.to1DSpan() << "\n";
583 B b{ w };
584 std::cout << b.a_.to1DSpan() << "\n";
585 return b;
586}
587
588auto bar2()
589{
591 tpq.fill(1.526);
592 std::cout << tpq.to1DSpan() << "\n";
593 return tpq;
594}
595
596} // namespace TestCopyNumArray
597
598TEST(NumArray, TestCopy)
599{
600 using namespace TestCopyNumArray;
601
602 auto test4 = bar();
603 std::cout << "Val 4 = "
604 << &test4.a_
605 << " " << test4.a_.to1DSpan() << "\n";
606 auto test5 = bar2();
607 std::cout << "Val 5 = " << &test5 << " " << test5.to1DSpan() << "\n";
608 ASSERT_EQ(test4.a_.to1DSpan(), test5.to1DSpan());
609}
610
611/*---------------------------------------------------------------------------*/
612/*---------------------------------------------------------------------------*/
613
614namespace Arcane
615{
616// On instantie explicitement pour tester que toutes les méthodes templates sont valides
620
624
625template class NumArray<float,MDDim1>;
626
632
636
640
641template class MDSpan<float,MDDim1>;
642
648}
649
650/*---------------------------------------------------------------------------*/
651/*---------------------------------------------------------------------------*/
#define ASSERT_TRUE(condition)
Vérifie que condition est vrai.
Definition Assertion.h:126
Lecteur des fichiers de maillage via la bibliothèque LIMA.
Definition Lima.cc:120
Tableaux multi-dimensionnels pour les types numériques accessibles sur accélérateurs.
Classe gérant un vecteur de réel de dimension 2.
Definition Real2.h:121
Classe gérant une matrice de réel de dimension 2x2.
Definition Real2x2.h:53
Classe gérant un vecteur de réel de dimension 3.
Definition Real3.h:132
Classe gérant une matrice de réel de dimension 3x3.
Definition Real3x3.h:66
void readFromText(NumArray< double, MDDim1 > &v, std::istream &input)
Remplit v avec les valeurs de input.
-*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-