1 // Copyright (C) 2007-2008 CEA/DEN, EDF R&D, OPEN CASCADE
3 // Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
22 #include "MEDMEMTest.hxx"
23 #include <cppunit/Message.h>
24 #include <cppunit/TestAssert.h>
26 #include "MEDMEM_Array.hxx"
27 #include "MEDMEM_Coordinate.hxx"
32 // use this define to enable lines, execution of which leads to Segmentation Fault
33 //#define ENABLE_FAULTS
35 // use this define to enable CPPUNIT asserts and fails, showing bugs
36 //#define ENABLE_FORCED_FAILURES
39 using namespace MEDMEM;
41 // #8: MEDMEM_Coordinate.hxx } MEDMEMTest_Coordinate.cxx
44 * Check methods (23), defined in MEDMEM_Coordinate.hxx:
47 * (+) COORDINATE(int SpaceDimension, int NumberOfNodes, MED_EN::medModeSwitch Mode);
48 * (+) COORDINATE(int SpaceDimension,const string * CoordinateName, const string * CoordinateUnit);
49 * (+) COORDINATE(const COORDINATE & m);
50 * (+) virtual ~COORDINATE();
51 * (+) void setCoordinates(MEDARRAY<double> *Coordinate,bool shallowCopy=false);
52 * (+) void setCoordinates(const MED_EN::medModeSwitch Mode, const double *Coordinate);
53 * (+) void setCoordinatesNames(const string * CoordinateName);
54 * (+) void setCoordinateName(const string CoordinateName, const int i);
55 * (+) void setCoordinatesUnits(const string * CoordinateUnit);
56 * (+) void setCoordinateUnit(const string CoordinateUnit, const int i);
57 * (+) void setCoordinatesSystem(const string CoordinateSystem);
58 * (+) void setNodesNumbers(const int * NodeNumber);
59 * (+) int getSpaceDimension() const;
60 * (+) int getNumberOfNodes() const;
61 * (+) virtual const int* getNodesNumbers() const;
62 * (+) string getCoordinatesSystem() const;
63 * (+) virtual const double * getCoordinates(MED_EN::medModeSwitch Mode);
64 * (+) virtual double getCoordinate(int Number,int Axis);
65 * (+) virtual const double * getCoordinateAxis(int Axis);
66 * (+) const string * getCoordinatesNames() const;
67 * (+) string getCoordinateName(int Axis) const;
68 * (+) const string * getCoordinatesUnits() const;
69 * (+) string getCoordinateUnit(int Axis) const;
72 * Use code of MEDMEM/tests/testUCoordinate.cxx
73 * MEDMEM/test_copie_coordinate.cxx
75 void MEDMEMTest::testCoordinate()
77 //////////////////////////////////////////////
78 // TEST 1: MEDMEM/tests/testUCoordinate.cxx //
79 //////////////////////////////////////////////
81 const double pouieme = 0.009;
86 string * noms = new string[3];
96 int * numbers = new int[5];
97 for (int i = 0; i < 5; i++) numbers[i] = 10 + i;
99 double coor[15] = {0,0,0,0,0,1,0,1,0,1,0,0,0.5,0.5,0.5};
100 CPPUNIT_ASSERT(SpaceDim * NbOfNodes == 15);
102 double * coor1 = new double [SpaceDim*NbOfNodes];
103 for (int k = 0; k < SpaceDim*NbOfNodes; k++)
106 MEDARRAY<double>* CoordinateArray =
107 new MEDARRAY<double>(coor1, SpaceDim, NbOfNodes, MED_EN::MED_FULL_INTERLACE);
109 CPPUNIT_ASSERT_NO_THROW(mycoo.setCoordinates(CoordinateArray));
111 //--------------------------------------------------------------------//
112 // Tests des methodes //
114 // - setCoordinatesNames //
115 // - setCoordinatesUnits //
116 // - setCoordinatesSystem //
117 // - setNodesNumbers //
119 //--------------------------------------------------------------------//
121 CPPUNIT_ASSERT_NO_THROW(mycoo.setCoordinatesNames(noms));
122 CPPUNIT_ASSERT_NO_THROW(mycoo.setCoordinatesUnits(units));
123 CPPUNIT_ASSERT_NO_THROW(mycoo.setCoordinatesSystem("cartesien"));
124 CPPUNIT_ASSERT_NO_THROW(mycoo.setNodesNumbers(numbers));
126 //--------------------------------------------------------------------//
127 // Tests des methodes //
129 // - getCoordinatesNames //
130 // - getCoordinatesUnits //
131 // - getCoordinatesUnit //
132 // - getCoordinatesSystem //
133 // - getNodesNumbers //
135 //--------------------------------------------------------------------//
136 CPPUNIT_ASSERT_NO_THROW(CPPUNIT_ASSERT(mycoo.getCoordinatesSystem() == "cartesien"));
138 const string * units2;
141 units2 = mycoo.getCoordinatesUnits();
142 for (int axe = 0; axe < SpaceDim; axe++) {
143 string verif = mycoo.getCoordinateUnit(axe+1);
144 CPPUNIT_ASSERT(verif == units2[axe]);
147 catch (const std::exception &e)
149 CPPUNIT_FAIL(e.what());
153 CPPUNIT_FAIL("Unknown exception");
156 const string * noms2;
159 noms2 = mycoo.getCoordinatesNames();
160 for (int axe = 0; axe < SpaceDim; axe++) {
161 string verif = mycoo.getCoordinateName(axe+1);
162 CPPUNIT_ASSERT(verif == noms2[axe]);
165 catch (const std::exception &e)
167 CPPUNIT_FAIL(e.what());
171 CPPUNIT_FAIL("Unknown exception");
176 const double * coor2 = mycoo.getCoordinates(MED_EN::MED_FULL_INTERLACE);
178 for (int axe = 0; axe < SpaceDim; axe++) {
179 const double * coor3 = mycoo.getCoordinateAxis(axe+1);
180 for (int num = 0; num < NbOfNodes; num++) {
181 const double d = mycoo.getCoordinate(num + 1, axe + 1);
182 CPPUNIT_ASSERT(fabs(d - coor3[num ]) < pouieme);
183 CPPUNIT_ASSERT(fabs(d - coor2[(num * SpaceDim)+axe]) < pouieme);
184 CPPUNIT_ASSERT(fabs(d - coor [(num * SpaceDim)+axe]) < pouieme);
188 catch (const std::exception &e)
190 CPPUNIT_FAIL(e.what());
194 CPPUNIT_FAIL("Unknown exception");
201 delete CoordinateArray;
204 //////////////////////////////////////////////
205 // TEST 2: MEDMEM/test_copie_coordinate.cxx //
206 //////////////////////////////////////////////
208 const int numberofNodes = 5;
209 const int spaceDimension = 3;
210 const MED_EN::medModeSwitch mode = MED_EN::MED_FULL_INTERLACE;
212 //construction tableau MEDARRAY des coordonnées
213 MEDARRAY<double> * myMedArray = new MEDARRAY<double>(spaceDimension, numberofNodes, mode);
214 for (int i = 1; i <= myMedArray->getLengthValue(); i++) {
215 for (int j = 1; j <= myMedArray->getLeadingValue(); j++)
216 myMedArray->setIJ(i, j, (double) i*j);
219 //construction noms des coordonnées
220 string * myCoordinatesNames = new string[spaceDimension];
221 if (spaceDimension >= 1) myCoordinatesNames[0] = "x";
222 if (spaceDimension >= 2) myCoordinatesNames[1] = "y";
223 if (spaceDimension >= 3) myCoordinatesNames[2] = "z";
225 //construction unités des coordonnées
226 string * myCoordinatesUnits = new string[spaceDimension];
227 if (spaceDimension >= 1) myCoordinatesUnits[0] = "m";
228 if (spaceDimension >= 2) myCoordinatesUnits[1] = "m";
229 if (spaceDimension >= 3) myCoordinatesUnits[2] = "m";
231 //construction des indices des noeuds
232 int * myNodeNumber = new int[numberofNodes];
233 for (int i = 0; i < numberofNodes; i++)
234 myNodeNumber[i] = numberofNodes - i - 1;
236 //construction de l'objet COORDINATE
237 COORDINATE * myCoordinate = new COORDINATE();
238 myCoordinate->setCoordinates(myMedArray);
239 myCoordinate->setCoordinatesNames(myCoordinatesNames);
240 myCoordinate->setCoordinatesUnits(myCoordinatesUnits);
241 myCoordinate->setNodesNumbers(myNodeNumber);
244 delete[] myCoordinatesNames;
245 delete[] myCoordinatesUnits;
246 delete[] myNodeNumber;
248 COORDINATE * myCoordinate2 = new COORDINATE(* myCoordinate);
252 // check copied coordinate
253 int _spaceDimension = myCoordinate2->getSpaceDimension();
254 int _numberofNodes = myCoordinate2->getNumberOfNodes();
255 CPPUNIT_ASSERT(_spaceDimension == spaceDimension);
256 CPPUNIT_ASSERT(_numberofNodes == numberofNodes);
258 for (int i = 1; i <= _numberofNodes; i++) {
259 for (int j = 1; j <= _spaceDimension; j++) {
260 CPPUNIT_ASSERT_DOUBLES_EQUAL(i*j, myCoordinate2->getCoordinate(i, j), 0.000001);
264 CPPUNIT_ASSERT(myCoordinate2->getCoordinateName(1) == "x");
265 CPPUNIT_ASSERT(myCoordinate2->getCoordinateName(2) == "y");
266 CPPUNIT_ASSERT(myCoordinate2->getCoordinateName(3) == "z");
268 CPPUNIT_ASSERT(myCoordinate2->getCoordinateUnit(1) == "m");
269 CPPUNIT_ASSERT(myCoordinate2->getCoordinateUnit(2) == "m");
270 CPPUNIT_ASSERT(myCoordinate2->getCoordinateUnit(3) == "m");
272 for (int i = 0; i < _numberofNodes; i++)
273 CPPUNIT_ASSERT(myCoordinate2->getNodesNumbers()[i] == _numberofNodes - i - 1);
275 delete myCoordinate2;
282 // COORDINATE(int SpaceDimension, int NumberOfNodes, MED_EN::medModeSwitch Mode);
283 COORDINATE anEmptyC (2, 10, MED_EN::MED_FULL_INTERLACE);
284 CPPUNIT_ASSERT(anEmptyC.getSpaceDimension() == 2);
285 CPPUNIT_ASSERT(anEmptyC.getNumberOfNodes() == 10);
286 CPPUNIT_ASSERT(anEmptyC.getNodesNumbers() == NULL);
287 // ?: how to fill it with coordinates?
288 // 1. void setCoordinates(MEDARRAY<double> *Coordinate,bool shallowCopy=false);
289 // but this way we can override all three constructor parameters
290 // 2. void setCoordinates(const MED_EN::medModeSwitch Mode, const double *Coordinate);
291 // in this case we can override Mode
293 //#ifdef ENABLE_FAULTS
294 // (BUG) Incoherence between setCoordinateName() and getCoordinateName()
295 //anEmptyC.setCoordinateName("alpha", 1);
296 //anEmptyC.setCoordinateName("betta", 2);
297 // (BUG) Incoherence between setCoordinateUnit() and getCoordinateUnit()
298 //anEmptyC.setCoordinateUnit("ttt", 1);
299 //anEmptyC.setCoordinateUnit("sss", 2);
301 anEmptyC.setCoordinateName("alpha", 0);
302 anEmptyC.setCoordinateName("betta", 1);
304 anEmptyC.setCoordinateUnit("ttt", 0);
305 anEmptyC.setCoordinateUnit("sss", 1);
307 //#ifdef ENABLE_FORCED_FAILURES
308 //CPPUNIT_FAIL("Incoherence between COORDINATE::setCoordinateName() and COORDINATE::getCoordinateName()");
309 //CPPUNIT_FAIL("Incoherence between COORDINATE::setCoordinateUnit() and COORDINATE::getCoordinateUnit()");
313 double * cc = new double[len];
314 for (int i = 0; i < len; i++) {
315 cc[i] = (double)(i + 1);
317 anEmptyC.setCoordinates(MED_EN::MED_NO_INTERLACE, cc);
319 CPPUNIT_ASSERT(anEmptyC.getCoordinateName(1) == "alpha");
320 CPPUNIT_ASSERT(anEmptyC.getCoordinateName(2) == "betta");
321 CPPUNIT_ASSERT(anEmptyC.getCoordinateUnit(1) == "ttt");
322 CPPUNIT_ASSERT(anEmptyC.getCoordinateUnit(2) == "sss");
323 for (int nn = 1; nn <= 10; nn++) {
324 for (int aa = 1; aa <= 2; aa++) {
325 CPPUNIT_ASSERT_DOUBLES_EQUAL(nn + (aa - 1) * 10, anEmptyC.getCoordinate(nn, aa), 0.000001);
329 CPPUNIT_ASSERT_THROW(anEmptyC.getCoordinate(0, 0), MEDEXCEPTION);
330 CPPUNIT_ASSERT_THROW(anEmptyC.getCoordinate(10, 10), MEDEXCEPTION);
332 MEDARRAY<double> mcc (cc, 2, 10, MED_EN::MED_FULL_INTERLACE, false, false);
333 anEmptyC.setCoordinates(&mcc, false);
335 // coordinates names and units are not changed
336 CPPUNIT_ASSERT(anEmptyC.getCoordinateName(1) == "alpha");
337 CPPUNIT_ASSERT(anEmptyC.getCoordinateName(2) == "betta");
338 CPPUNIT_ASSERT(anEmptyC.getCoordinateUnit(1) == "ttt");
339 CPPUNIT_ASSERT(anEmptyC.getCoordinateUnit(2) == "sss");
340 for (int nn = 1; nn <= 10; nn++) {
341 for (int aa = 1; aa <= 2; aa++) {
342 // coordinates changed
343 CPPUNIT_ASSERT_DOUBLES_EQUAL((nn - 1) * 2 + aa, anEmptyC.getCoordinate(nn, aa), 0.000001);
349 //#ifdef ENABLE_FAULTS
350 // (BUG) Segmentation Fault or Hang up after anEmptyC and mcc destruction,
351 // because array will be owned by two pointers (in mcc and in anEmptyC) after this call
352 //???skl anEmptyC.setCoordinates(&mcc, true);
353 // In other case (if we dynamically allocate mcc and do not free it) we will have memory leak.
355 //#ifdef ENABLE_FORCED_FAILURES
356 //CPPUNIT_FAIL("Bug in COORDINATE::setCoordinates() in shallow copy mode");
364 // COORDINATE(int SpaceDimension,const string * CoordinateName, const string * CoordinateUnit);
365 string cnames [3] = {"al", "be", "ga"};
366 string cunits [3] = {"kg", "mm", "s2"};
367 COORDINATE anEmptyA (3, cnames, cunits);
369 CPPUNIT_ASSERT(anEmptyA.getCoordinateName(1) == "al");
370 CPPUNIT_ASSERT(anEmptyA.getCoordinateName(2) == "be");
371 CPPUNIT_ASSERT(anEmptyA.getCoordinateName(3) == "ga");
373 CPPUNIT_ASSERT(anEmptyA.getCoordinateUnit(1) == "kg");
374 CPPUNIT_ASSERT(anEmptyA.getCoordinateUnit(2) == "mm");
375 CPPUNIT_ASSERT(anEmptyA.getCoordinateUnit(3) == "s2");
377 CPPUNIT_ASSERT_EQUAL(anEmptyA.getSpaceDimension(), 0);
378 CPPUNIT_ASSERT_EQUAL(anEmptyA.getNumberOfNodes(), 0);
380 MEDARRAY<double> mcc (3, 7, MED_EN::MED_NO_INTERLACE);
381 anEmptyA.setCoordinates(&mcc, false);
383 CPPUNIT_ASSERT_EQUAL(anEmptyA.getSpaceDimension(), 3);
384 CPPUNIT_ASSERT_EQUAL(anEmptyA.getNumberOfNodes(), 7);
386 CPPUNIT_ASSERT(anEmptyA.getCoordinateName(1) == "al");
387 CPPUNIT_ASSERT(anEmptyA.getCoordinateName(2) == "be");
388 CPPUNIT_ASSERT(anEmptyA.getCoordinateName(3) == "ga");
390 CPPUNIT_ASSERT(anEmptyA.getCoordinateUnit(1) == "kg");
391 CPPUNIT_ASSERT(anEmptyA.getCoordinateUnit(2) == "mm");
392 CPPUNIT_ASSERT(anEmptyA.getCoordinateUnit(3) == "s2");
394 CPPUNIT_ASSERT_THROW(anEmptyA.getCoordinate(-1, 0), MEDEXCEPTION);
395 CPPUNIT_ASSERT_THROW(anEmptyA.getCoordinate(10, 10), MEDEXCEPTION);
397 // No COORDINATE::operator=, but this is compilable
399 //COORDINATE anEmptyB;
400 //COORDINATE anEmptyD (3, cnames, cunits);
401 //anEmptyB = anEmptyD;
402 //CPPUNIT_ASSERT(anEmptyB.getCoordinateName(1) == "al");
404 // bad (assert fails)
405 //COORDINATE anEmptyB;
406 // Object, created in this line, is destructed right after it.
407 //anEmptyB = COORDINATE(3, cnames, cunits);
408 // Now a pointer _coordinateName inside anEmptyB points to a desallocated memory zone
409 //CPPUNIT_ASSERT(anEmptyB.getCoordinateName(1) == "al");