Salome HOME
7d247e1b7e191f509fdc9742c977714b84121e52
[modules/med.git] / src / MEDMEMCppTest / MEDMEMTest_AsciiFieldDriver.cxx
1 // Copyright (C) 2007-2013  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License.
7 //
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19
20 #include "MEDMEMTest.hxx"
21 #include <cppunit/TestAssert.h>
22
23 #include "MEDMEM_AsciiFieldDriver.hxx"
24 #include "MEDMEM_STRING.hxx"
25
26 #include <stdio.h>
27
28 #include <sstream>
29 #include <fstream>
30 #include <cmath>
31
32 // use this define to enable lines, execution of which leads to Segmentation Fault
33 //#define ENABLE_FAULTS
34
35 // use this define to enable CPPUNIT asserts and fails, showing bugs
36 //#define ENABLE_FORCED_FAILURES
37
38 using namespace std;
39 using namespace MEDMEM;
40
41 // #4: MEDMEM_AsciiFieldDriver.hxx  }  MEDMEMTest_AsciiFieldDriver.cxx
42
43 /*!
44  *  Check methods (8), defined in MEDMEM_AsciiFieldDriver.hxx:
45  *
46  *  (+)     template<int N,unsigned int CODE> void fill(double *a, const double *b)
47  *  (+)     template<int N> bool compare(const double* a, const double* b)
48  *  (+)     template<> void fill<-1,0x3>(double *a, const double *b);
49  *  (+)     template<> bool compare<-1>(const double *a, const double *b);
50  *
51  *  template <class T, int SPACEDIMENSION, unsigned int SORTSTRATEGY>
52  *  class SDForSorting {
53  *   (+)     SDForSorting(const double *coords, const T* comp, int nbComponents);
54  *   (+)     SDForSorting(const SDForSorting& other);
55  *   (+)     ~SDForSorting();
56  *   (+)     bool operator< (const SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>& other) const;
57  *   (+)     void writeLine(ofstream& file) const;
58  *  }
59  *
60  *  template <class T>
61  *  class ASCII_FIELD_DRIVER : public GENDRIVER {
62  *
63  *           //MUST BE PRIVATE as there is no possibility to set _ptrField after this constructor usage
64  *   (-)     template <class INTERLACING_TAG> ASCII_FIELD_DRIVER();
65  *
66  *   (+)     template <class INTERLACING_TAG>
67  *           ASCII_FIELD_DRIVER(const string & fileName, FIELD<T,INTERLACING_TAG> * ptrField,
68  *                              MED_EN::med_sort_direc direction=MED_EN::ASCENDING, const char *priority="");
69  *   (+)     ASCII_FIELD_DRIVER(const ASCII_FIELD_DRIVER<T>& other);
70  *   (+)     void open() throw (MEDEXCEPTION);
71  *   (+)     void close();
72  *   (+)     void read (void) throw (MEDEXCEPTION);
73  *   (+)     void write(void) const throw (MEDEXCEPTION);
74  *   (+)     GENDRIVER* copy() const;
75  *  }
76  */
77 void MEDMEMTest::testAsciiFieldDriver()
78 {
79   // read a mesh from a MED file
80   string filename  = getResourceFile("pointe.med");
81   string meshname  = "maa1";
82   string fieldname = "fieldcelldoublescalar";
83
84   string anyfile1    = makeTmpFile( "anyfile1" );
85   string SDFfilename = makeTmpFile( "myfile" );
86   ofstream aFile(SDFfilename.c_str());
87
88   // To remove tmp files from disk
89   MEDMEMTest_TmpFilesRemover aRemover;
90   aRemover.Register(anyfile1);
91   aRemover.Register(SDFfilename);
92
93   //Test SDForSorting class
94   {
95     double coord_1[10] = { 1.0, 2.0,
96                            -1.0, 2.0,
97                            3.6, -8.7,
98                            10.0, -10.0,
99                            12.3, 9.3};
100
101     int comp_1[5] = {1, 3, 5, 7, 9};
102     SDForSorting<int, 2, 48> aSDF_1(coord_1, comp_1, 5);
103
104     SDForSorting<int, 2, 48> aSDFCpy_1 = SDForSorting<int, 2, 48>(aSDF_1);
105     CPPUNIT_ASSERT_EQUAL(aSDFCpy_1 < aSDF_1, false);
106     CPPUNIT_ASSERT_NO_THROW(aSDF_1.writeLine(aFile));
107   }
108
109   // Why functions
110   // template<> void MEDMEM::fill<-1,0x3>(double *a, const double *b)
111   // and
112   // template<> bool MEDMEM::compare<-1>(const double *a, const double *b)
113   // declared in MEDMEM_AsciiFieldDriver.hxx,
114   // are implemented in MEDMEM_DriverFactory.cxx?
115
116   // template<int N,unsigned int CODE> void fill(double *a, const double *b)
117   {
118     // 0x3 = 110000
119     double aa[3];
120     double bb[3] = {1,2,3};
121
122     fill<2,198>(aa, bb); // ZYX // 11000110 // 012
123     //MEDMEMTest_DumpArray<double>(cout, aa, 3, "aa filled with ZYX");
124     CPPUNIT_ASSERT_EQUAL(aa[0], bb[0]);
125     CPPUNIT_ASSERT_EQUAL(aa[1], bb[1]);
126     CPPUNIT_ASSERT_EQUAL(aa[2], bb[2]);
127
128     fill<2,210>(aa, bb); // ZXY // 11010010 // 102
129     //MEDMEMTest_DumpArray<double>(cout, aa, 3, "aa filled with ZXY");
130     CPPUNIT_ASSERT_EQUAL(aa[0], bb[1]);
131     CPPUNIT_ASSERT_EQUAL(aa[1], bb[0]);
132     CPPUNIT_ASSERT_EQUAL(aa[2], bb[2]);
133
134     fill<2,228>(aa, bb); // XYZ // 11100100 // 210
135     //MEDMEMTest_DumpArray<double>(cout, aa, 3, "aa filled with XYZ");
136     CPPUNIT_ASSERT_EQUAL(aa[0], bb[2]);
137     CPPUNIT_ASSERT_EQUAL(aa[1], bb[1]);
138     CPPUNIT_ASSERT_EQUAL(aa[2], bb[0]);
139   }
140
141   // template<int N> bool compare(const double* a, const double* b)
142   {
143     {
144       // aa < bb
145       double aa[8] = {1,1,1,1,1,1,1,1};
146       double bb[8] = {1,1,1,1,1,1,1,2};
147       CPPUNIT_ASSERT(compare<7>(aa, bb));
148     }
149
150     {
151       // aa < bb
152       double aa[8] = {1,1,1,1,1,1,1,1};
153       double bb[8] = {2,1,1,1,1,1,1,1};
154       CPPUNIT_ASSERT(compare<7>(aa, bb));
155     }
156
157     {
158       // aa > bb
159       double aa[8] = {2,1,1,1,1,1,1,1};
160       double bb[8] = {1,1,1,1,1,1,1,1};
161       CPPUNIT_ASSERT(!compare<7>(aa, bb));
162     }
163
164     {
165       // aa == bb
166       double aa[8] = {1,1,1,1,1,1,1,1};
167       double bb[8] = {1,1,1,1,1,1,1,1};
168       CPPUNIT_ASSERT(!compare<7>(aa, bb));
169     }
170
171     {
172       // compare<-1>
173       double aa[8] = {2,1,1,1,1,1,1,1};
174       double bb[8] = {1,1,1,1,1,1,1,1};
175       CPPUNIT_ASSERT(!compare<-1>(aa, bb));
176     }
177   }
178
179   // Test ASCII_FIELD_DRIVER
180   FIELD<double> * aField1 = new FIELD<double> (MED_DRIVER, filename, fieldname);
181   const SUPPORT * aSupport = aField1->getSupport();
182   MESH * aMesh = new MESH(MED_DRIVER, filename, aSupport->getMeshName());
183   aSupport->setMesh(aMesh);
184
185   // create an ASCII driver for a field
186   ASCII_FIELD_DRIVER<double> * aDriver1 =
187     new ASCII_FIELD_DRIVER<double> (anyfile1, aField1, MED_EN::ASCENDING, "");
188   CPPUNIT_ASSERT(aDriver1);
189
190   CPPUNIT_ASSERT(aDriver1->getFileName() == anyfile1);
191   CPPUNIT_ASSERT(aDriver1->getAccessMode() == MED_EN::WRONLY);
192
193   // and write the field on disk
194
195   // must throw because the file is not opened
196
197   CPPUNIT_ASSERT_THROW(aDriver1->write(), MEDEXCEPTION);
198
199   aDriver1->open();
200
201   // must throw because the file is opened
202   CPPUNIT_ASSERT_THROW(aDriver1->setFileName("anyfile2"), MEDEXCEPTION);
203   CPPUNIT_ASSERT_THROW(aDriver1->setFileName(anyfile1), MEDEXCEPTION);
204
205   CPPUNIT_ASSERT_THROW(aDriver1->open(), MEDEXCEPTION);
206
207
208   // must throw because it is a writeonly driver
209   CPPUNIT_ASSERT_THROW(aDriver1->read(), MEDEXCEPTION);
210
211   aDriver1->write();
212   aDriver1->close();
213
214   // must throw because the file is not opened
215
216   CPPUNIT_ASSERT_THROW(aDriver1->write(), MEDEXCEPTION);
217
218   //CPPUNIT_ASSERT_THROW(aDriver1->close(), MEDEXCEPTION);
219   CPPUNIT_ASSERT_NO_THROW(aDriver1->close()); // do not make troubles to the user
220
221   // check priority definition
222   int spaceDimension = aMesh->getSpaceDimension();
223   if (spaceDimension == 3) {
224     // good
225     CPPUNIT_ASSERT_NO_THROW(ASCII_FIELD_DRIVER<double> aDriver2
226                             ("anyfile2", aField1, MED_EN::ASCENDING, "XYZ"));
227     // too long
228     CPPUNIT_ASSERT_THROW(ASCII_FIELD_DRIVER<double> aDriver3
229                          ("anyfile3", aField1, MED_EN::ASCENDING, "XYZX"), MEDEXCEPTION);
230     // too short
231     CPPUNIT_ASSERT_THROW(ASCII_FIELD_DRIVER<double> aDriver4
232                          ("anyfile4", aField1, MED_EN::ASCENDING, "XY"), MEDEXCEPTION);
233     // invalid
234     CPPUNIT_ASSERT_THROW(ASCII_FIELD_DRIVER<double> aDriver5
235                          ("anyfile5", aField1, MED_EN::ASCENDING, "ABC"), MEDEXCEPTION);
236   }
237   else if (spaceDimension == 2) {
238     // good
239     CPPUNIT_ASSERT_NO_THROW(ASCII_FIELD_DRIVER<double> aDriver2
240                             ("anyfile2", aField1, MED_EN::ASCENDING, "XY"));
241     // too long
242     CPPUNIT_ASSERT_THROW(ASCII_FIELD_DRIVER<double> aDriver3
243                          ("anyfile3", aField1, MED_EN::ASCENDING, "XYZ"), MEDEXCEPTION);
244     // too short
245     CPPUNIT_ASSERT_THROW(ASCII_FIELD_DRIVER<double> aDriver4
246                          ("anyfile4", aField1, MED_EN::ASCENDING, "X"), MEDEXCEPTION);
247     // invalid
248     CPPUNIT_ASSERT_THROW(ASCII_FIELD_DRIVER<double> aDriver5
249                          ("anyfile5", aField1, MED_EN::ASCENDING, "AB"), MEDEXCEPTION);
250   }
251   else {
252     CPPUNIT_FAIL("Cannot test ASCII_FIELD_DRIVER because file pointe.med"
253                  " contains mesh of wrong dimension: must be 2 or 3");
254   }
255
256   //Copy constructor
257   ASCII_FIELD_DRIVER<double> aDriver1_Cpy1 = ASCII_FIELD_DRIVER<double> (*aDriver1);
258
259   //Test copy() function
260   ASCII_FIELD_DRIVER<double> *aDriver1_Cpy2 = (ASCII_FIELD_DRIVER<double>*)aDriver1->copy();
261   CPPUNIT_ASSERT(aDriver1_Cpy2);
262   delete aDriver1_Cpy2;
263   // free memory
264   delete aDriver1;
265   aField1->removeReference();
266   aMesh->removeReference();
267 }