1 #ifndef ASCII_FIELD_DRIVER_HXX
2 #define ASCII_FIELD_DRIVER_HXX
4 #include "MEDMEM_Mesh.hxx"
5 #include "MEDMEM_Support.hxx"
6 #include "MEDMEM_GenDriver.hxx"
7 #include "MEDMEM_Exception.hxx"
8 #include "MEDMEM_Unit.hxx"
18 #define PRECISION_IN_ASCII_FILE 10
19 #define PRECISION_IN_COMPARE 1e-10
20 #define SPACE_BETWEEN_NBS 19
27 template<int N,unsigned int CODE>
28 void fill(double *a, const double *b)
31 fill<N-1, (CODE>>2) >(a,b);
35 bool compare(const double* a, const double* b)
37 double sign=b[N]<0 ? -1 : 1;
38 if(a[N]<b[N]*(1-sign*PRECISION_IN_COMPARE))
40 if(a[N]>b[N]*(1+sign*PRECISION_IN_COMPARE))
42 return compare<N-1>(a,b);
46 void fill<-1,0x3>(double *a, const double *b);
49 bool compare<-1>(const double *a, const double *b);
51 template <class T, int SPACEDIMENSION, unsigned int SORTSTRATEGY>
55 double _coords[SPACEDIMENSION];
59 SDForSorting(const double *coords, const T* comp, int nbComponents);
60 SDForSorting(const SDForSorting& other);
62 bool operator< (const SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>& other) const;
63 void writeLine(ofstream& file) const;
67 class ASCII_FIELD_DRIVER : public GENDRIVER
72 mutable FIELD<T> * _ptrField;
73 std::string _fileName;
74 mutable ofstream _file;
76 MED_EN::med_sort_direc _direc;
79 //static int _nbComponentsForCpyInfo;
81 ASCII_FIELD_DRIVER(const string & fileName, FIELD<T> * ptrField,
82 MED_EN::med_sort_direc direction=MED_EN::ASCENDING,
83 const char *priority="");
84 ASCII_FIELD_DRIVER(const ASCII_FIELD_DRIVER<T>& other);
85 void open() throw (MEDEXCEPTION);
87 void read ( void ) throw (MEDEXCEPTION);
88 void write( void ) const throw (MEDEXCEPTION);
89 GENDRIVER* copy() const;
91 void buildIntroduction() const;
92 template<int SPACEDIMENSION, unsigned int SORTSTRATEGY>
93 void sortAndWrite() const;
94 //template<int SPACEDIMENSION, unsigned int SORTSTRATEGY>//, std::list< SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY > > >
95 //static void copyInfo(const double *a,T *b);
96 //static void copyInfo2(const double *,T *);
100 #include "MEDMEM_Field.hxx"
104 template <class T, int SPACEDIMENSION, unsigned int SORTSTRATEGY>
105 SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>::SDForSorting(const double *coords, const T* comp, int nbComponents):_nbComponents(nbComponents)
107 fill<SPACEDIMENSION-1,SORTSTRATEGY>(_coords,coords);
108 _components=new T[_nbComponents];
109 memcpy(_components,comp,sizeof(T)*_nbComponents);
112 template <class T, int SPACEDIMENSION, unsigned int SORTSTRATEGY>
113 SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>::SDForSorting(const SDForSorting& other):_nbComponents(other._nbComponents)
115 memcpy(_coords,other._coords,sizeof(double)*SPACEDIMENSION);
116 _components=new T[_nbComponents];
117 memcpy(_components,other._components,sizeof(T)*_nbComponents);
120 template <class T, int SPACEDIMENSION, unsigned int SORTSTRATEGY>
121 SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>::~SDForSorting()
123 delete [] _components;
126 template <class T, int SPACEDIMENSION, unsigned int SORTSTRATEGY>
127 bool SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>::operator< (const SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>& other) const
129 return compare<SPACEDIMENSION-1>(_coords,other._coords);
132 template <class T, int SPACEDIMENSION, unsigned int SORTSTRATEGY>
133 void SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>::writeLine(ofstream& file) const
136 double temp[SPACEDIMENSION];
137 fill<SPACEDIMENSION-1,SORTSTRATEGY>(temp,_coords);
138 for(i=0;i<SPACEDIMENSION;i++)
139 file << setw(SPACE_BETWEEN_NBS) << temp[i];
140 for(i=0;i<_nbComponents;i++)
141 file << setw(SPACE_BETWEEN_NBS) << _components[i];
146 ASCII_FIELD_DRIVER<T>::ASCII_FIELD_DRIVER(const string & fileName, FIELD<T> * ptrField,
147 MED_EN::med_sort_direc direction,const char *priority)
148 :GENDRIVER(fileName,MED_EN::MED_ECRI),_ptrField(ptrField),_fileName(fileName),_direc(direction)
150 _nbComponents=_ptrField->getNumberOfComponents();
152 throw MEDEXCEPTION("ASCII_FIELD_DRIVER : No components in FIELD<T>");
153 _support=(SUPPORT *)_ptrField->getSupport();
154 _mesh=(MESH *)_support->getMesh();
155 _spaceDimension=_mesh->getSpaceDimension();
158 if(priority[0]=='\0')
159 for(i=_spaceDimension-1;i>=0;i--)
166 if(_spaceDimension!=strlen(priority))
167 throw MEDEXCEPTION("ASCII_FIELD_DRIVER : Coordinate priority invalid with spaceDim");
168 for(i=_spaceDimension-1;i>=0;i--)
170 char c=toupper(priority[i]);
171 if(int(c-'X')>(_spaceDimension-1))
172 throw MEDEXCEPTION("ASCII_FIELD_DRIVER : Invalid priority definition");
180 ASCII_FIELD_DRIVER<T>::ASCII_FIELD_DRIVER(const ASCII_FIELD_DRIVER<T>& other)
181 :_ptrField(other._ptrField),_fileName(other._fileName),_direc(other._direc),_mesh(other._mesh),_nbComponents(other._nbComponents),
182 _code(other._code),_spaceDimension(other._spaceDimension),_support(other._support)
187 void ASCII_FIELD_DRIVER<T>::open() throw (MEDEXCEPTION)
189 _file.open(_fileName.c_str(),ofstream::out | ofstream::app);
193 void ASCII_FIELD_DRIVER<T>::close()
199 void ASCII_FIELD_DRIVER<T>::read ( void ) throw (MEDEXCEPTION)
201 throw MEDEXCEPTION("ASCII_FIELD_DRIVER::read : Can't read with a WRONLY driver !");
205 GENDRIVER* ASCII_FIELD_DRIVER<T>::copy() const
207 return new ASCII_FIELD_DRIVER<T>(*this);
211 void ASCII_FIELD_DRIVER<T>::write( void ) const throw (MEDEXCEPTION)
214 switch(_spaceDimension)
222 sortAndWrite<2,52>();
227 sortAndWrite<2,49>();
231 MEDEXCEPTION("ASCII_FIELD_DRIVER : Invalid priority definition");
241 sortAndWrite<3,228>();
246 sortAndWrite<3,216>();
251 sortAndWrite<3,225>();
256 sortAndWrite<3,201>();
261 sortAndWrite<3,210>();
266 sortAndWrite<3,198>();
270 MEDEXCEPTION("ASCII_FIELD_DRIVER : Invalid priority definition");
275 MEDEXCEPTION("ASCII_FIELD_DRIVER : Invalid space dimension must be 2 or 3");
280 void ASCII_FIELD_DRIVER<T>::buildIntroduction() const
283 _file << setiosflags(ios::scientific);
284 _file << "#TITLE: table " << _ptrField->getName() << " TIME: " << _ptrField->getTime() << " IT: " << _ptrField->getIterationNumber() << endl;
285 _file << "#COLUMN_TITLES: ";
286 for(i=0;i<_spaceDimension;i++)
287 _file << char('X'+i) << " | ";
288 const std::string *compoNames=_ptrField->getComponentsNames();
289 for(i=0;i<_nbComponents;i++)
292 _file << compoNames[i];
295 if(i<_nbComponents-1)
299 _file << "#COLUMN_UNITS: ";
300 compoNames=_mesh->getCoordinateptr()->getCoordinatesUnits();
301 for(i=0;i<_spaceDimension;i++)
304 _file << compoNames[i];
309 const UNIT *compoUnits=_ptrField->getComponentsUnits();
310 for(i=0;i<_nbComponents;i++)
313 _file << compoUnits[i].getName();
316 if(i<_nbComponents-1)
323 template<int SPACEDIMENSION, unsigned int SORTSTRATEGY>
324 void ASCII_FIELD_DRIVER<T>::sortAndWrite() const
327 int numberOfValues=_ptrField->getNumberOfValues();
328 std::list< SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY > > li;
329 const double * coord;
330 FIELD<double> * barycenterField=0;
331 double * xyz[SPACEDIMENSION];
332 bool deallocateXyz=false;
333 if(_support->getEntity()==MED_EN::MED_NODE)
335 if (_support->isOnAllElements())
337 coord=_mesh->getCoordinates(MED_EN::MED_NO_INTERLACE);
338 for(i=0; i<SPACEDIMENSION; i++)
339 xyz[i]=(double *)coord+i*numberOfValues;
343 coord = _mesh->getCoordinates(MED_EN::MED_FULL_INTERLACE);
344 const int * nodesNumber=_support->getNumber(MED_EN::MED_ALL_ELEMENTS);
345 for(i=0; i<SPACEDIMENSION; i++)
346 xyz[i]=new double[numberOfValues];
348 for(i=0;i<numberOfValues;i++)
350 for(j=0;j<SPACEDIMENSION;j++)
351 xyz[j][i]=coord[(nodesNumber[i]-1)*SPACEDIMENSION+j];
357 barycenterField = _mesh->getBarycenter(_support);
358 coord=barycenterField->getValue(MED_EN::MED_NO_INTERLACE);
359 for(i=0; i<SPACEDIMENSION; i++)
360 xyz[i]=(double *)(coord+i*numberOfValues);
362 T* valsToSet=(T*)_ptrField->getValue(MED_EN::MED_FULL_INTERLACE);
363 double temp[SPACEDIMENSION];
364 for(i=0;i<numberOfValues;i++)
366 for(j=0;j<SPACEDIMENSION;j++)
368 li.push_back(SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>(temp,valsToSet+i*_nbComponents,_nbComponents));
371 delete barycenterField;
373 for(j=0;j<SPACEDIMENSION;j++)
376 _file << setprecision(PRECISION_IN_ASCII_FILE);
377 if(_direc==MED_EN::ASCENDING)
379 typename std::list< SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY > >::iterator iter;
380 for(iter=li.begin();iter!=li.end();iter++)
381 (*iter).writeLine(_file);
384 else if(_direc==MED_EN::DESCENDING)
386 typename std::list< SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY > >::reverse_iterator iter;
387 for(iter=li.rbegin();iter!=li.rend();iter++)
388 (*iter).writeLine(_file);
392 MEDEXCEPTION("ASCII_FIELD_DRIVER : Invalid sort direction");
395 //_nbComponentsForCpyInfo=_nbComponents;
396 //_ptrField->fillFromAnalytic <TEST<T>::copyInfo3> ();
397 //_ptrField->fillFromAnalytic< ASCII_FIELD_DRIVER<T>::copyInfo<SPACEDIMENSION,SORTSTRATEGY> > ();
399 //typename std::list< SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY > >::iterator iter;
400 //_file << setiosflags(ios::scientific) << setprecision(PRECISION_IN_ASCII_FILE);
401 //for(iter=li.begin();iter!=li.end();iter++)
403 //(*iter).writeLine(_file);
406 // template <class T>
407 // template<int SPACEDIMENSION, unsigned int SORTSTRATEGY>//, std::list< SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY> > lis>
408 // void ASCII_FIELD_DRIVER<T>::copyInfo(const double *a,T *b)
410 // //lis.push_back(SDForSorting<T,SPACEDIMENSION,SORTSTRATEGY>(a,b,_nbComponentsForCpyInfo));
413 // template <class T>
414 // int ASCII_FIELD_DRIVER<T>::_nbComponentsForCpyInfo=0;