1 // Copyright (C) 2007-2016 CEA/DEN, EDF R&D
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, or (at your option) any later version.
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.
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
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
19 // Author : Anthony Geay (CEA/DEN)
21 #include "MEDCouplingFieldDouble.hxx"
22 #include "MEDCouplingFieldTemplate.hxx"
23 #include "MEDCouplingFieldT.txx"
24 #include "MEDCouplingFieldInt.hxx"
25 #include "MEDCouplingUMesh.hxx"
26 #include "MEDCouplingTimeDiscretization.hxx"
27 #include "MEDCouplingFieldDiscretization.hxx"
29 #include "MEDCouplingVoronoi.hxx"
30 #include "MEDCouplingNatureOfField.hxx"
32 #include "InterpKernelAutoPtr.hxx"
33 #include "InterpKernelGaussCoords.hxx"
40 using namespace MEDCoupling;
42 template class MEDCoupling::MEDCouplingFieldT<double>;
45 * Creates a new MEDCouplingFieldDouble, of given spatial type and time discretization.
46 * For more info, see \ref MEDCouplingFirstSteps3.
47 * \param [in] type - the type of spatial discretization of the created field, one of
48 * (\ref MEDCoupling::ON_CELLS "ON_CELLS",
49 * \ref MEDCoupling::ON_NODES "ON_NODES",
50 * \ref MEDCoupling::ON_GAUSS_PT "ON_GAUSS_PT",
51 * \ref MEDCoupling::ON_GAUSS_NE "ON_GAUSS_NE",
52 * \ref MEDCoupling::ON_NODES_KR "ON_NODES_KR").
53 * \param [in] td - the type of time discretization of the created field, one of
54 * (\ref MEDCoupling::NO_TIME "NO_TIME",
55 * \ref MEDCoupling::ONE_TIME "ONE_TIME",
56 * \ref MEDCoupling::LINEAR_TIME "LINEAR_TIME",
57 * \ref MEDCoupling::CONST_ON_TIME_INTERVAL "CONST_ON_TIME_INTERVAL").
58 * \return MEDCouplingFieldDouble* - a new instance of MEDCouplingFieldDouble. The
59 * caller is to delete this field using decrRef() as it is no more needed.
61 MEDCouplingFieldDouble* MEDCouplingFieldDouble::New(TypeOfField type, TypeOfTimeDiscretization td)
63 return new MEDCouplingFieldDouble(type,td);
67 * Creates a new MEDCouplingFieldDouble, of a given time discretization and with a
68 * spatial type and supporting mesh copied from a given
69 * \ref MEDCouplingFieldTemplatesPage "field template".
70 * For more info, see \ref MEDCouplingFirstSteps3.
71 * \warning This method does not deeply copy neither the mesh nor the spatial
72 * discretization. Only a shallow copy (reference) is done for the mesh and the spatial
74 * \param [in] ft - the \ref MEDCouplingFieldTemplatesPage "field template" defining
75 * the spatial discretization and the supporting mesh.
76 * \param [in] td - the type of time discretization of the created field, one of
77 * (\ref MEDCoupling::NO_TIME "NO_TIME",
78 * \ref MEDCoupling::ONE_TIME "ONE_TIME",
79 * \ref MEDCoupling::LINEAR_TIME "LINEAR_TIME",
80 * \ref MEDCoupling::CONST_ON_TIME_INTERVAL "CONST_ON_TIME_INTERVAL").
81 * \return MEDCouplingFieldDouble* - a new instance of MEDCouplingFieldDouble. The
82 * caller is to delete this field using decrRef() as it is no more needed.
84 MEDCouplingFieldDouble *MEDCouplingFieldDouble::New(const MEDCouplingFieldTemplate& ft, TypeOfTimeDiscretization td)
86 return new MEDCouplingFieldDouble(ft,td);
90 * Sets a time \a unit of \a this field. For more info, see \ref MEDCouplingFirstSteps3.
91 * \param [in] unit \a unit (string) in which time is measured.
93 //void MEDCouplingFieldDouble::setTimeUnit(const std::string& unit)
96 * Returns a time unit of \a this field.
97 * \return a string describing units in which time is measured.
99 //std::string MEDCouplingFieldDouble::getTimeUnit() const
103 * This method if possible the time information (time unit, time iteration, time unit and time value) with its support
104 * that is to say its mesh.
106 * \throw If \c this->_mesh is null an exception will be thrown. An exception will also be throw if the spatial discretization is
109 void MEDCouplingFieldDouble::synchronizeTimeWithSupport()
111 timeDiscr()->synchronizeTimeWith(_mesh);
115 * Returns a new MEDCouplingFieldDouble which is a copy of \a this one. The data
116 * of \a this field is copied either deep or shallow depending on \a recDeepCpy
117 * parameter. But the underlying mesh is always shallow copied.
118 * Data that can be copied either deeply or shallow are:
119 * - \ref MEDCouplingTemporalDisc "temporal discretization" data that holds array(s)
121 * - \ref MEDCouplingSpatialDisc "a spatial discretization".
123 * \c clone(false) is rather dedicated for advanced users that want to limit the amount
124 * of memory. It allows the user to perform methods like operator+(), operator*()
125 * etc. with \a this and the returned field. If the user wants to duplicate deeply the
126 * underlying mesh he should call cloneWithMesh() method or deepCopy() instead.
127 * \warning The underlying \b mesh of the returned field is **always the same**
128 * (pointer) as \a this one **whatever the value** of \a recDeepCpy parameter.
129 * \param [in] recDeepCpy - if \c true, the copy of the underlying data arrays is
130 * deep, else all data arrays of \a this field are shared by the new field.
131 * \return MEDCouplingFieldDouble * - a new instance of MEDCouplingFieldDouble. The
132 * caller is to delete this field using decrRef() as it is no more needed.
133 * \sa cloneWithMesh()
135 MEDCouplingFieldDouble *MEDCouplingFieldDouble::clone(bool recDeepCpy) const
137 return new MEDCouplingFieldDouble(*this,recDeepCpy);
141 * Returns a new MEDCouplingFieldDouble which is a deep copy of \a this one **including
143 * The result of this method is exactly the same as that of \c cloneWithMesh(true).
144 * So the resulting field can not be used together with \a this one in the methods
145 * like operator+(), operator*() etc. To avoid deep copying the underlying mesh,
146 * the user can call clone().
147 * \return MEDCouplingFieldDouble * - a new instance of MEDCouplingFieldDouble. The
148 * caller is to delete this field using decrRef() as it is no more needed.
149 * \sa cloneWithMesh()
151 MEDCouplingFieldDouble *MEDCouplingFieldDouble::deepCopy() const
153 return cloneWithMesh(true);
157 * Creates a new MEDCouplingFieldDouble of given
158 * \ref MEDCouplingTemporalDisc "temporal discretization". The result field either
159 * shares the data array(s) with \a this field, or holds a deep copy of it, depending on
160 * \a deepCopy parameter. But the underlying \b mesh is always **shallow copied**.
161 * \param [in] td - the type of time discretization of the created field, one of
162 * (\ref MEDCoupling::NO_TIME "NO_TIME",
163 * \ref MEDCoupling::ONE_TIME "ONE_TIME",
164 * \ref MEDCoupling::LINEAR_TIME "LINEAR_TIME",
165 * \ref MEDCoupling::CONST_ON_TIME_INTERVAL "CONST_ON_TIME_INTERVAL").
166 * \param [in] deepCopy - if \c true, the copy of the underlying data arrays is
167 * deep, else all data arrays of \a this field are shared by the new field.
168 * \return MEDCouplingFieldDouble* - a new instance of MEDCouplingFieldDouble. The
169 * caller is to delete this field using decrRef() as it is no more needed.
171 * \if ENABLE_EXAMPLES
172 * \ref cpp_mcfielddouble_buildNewTimeReprFromThis "Here is a C++ example."<br>
173 * \ref py_mcfielddouble_buildNewTimeReprFromThis "Here is a Python example."
177 MEDCouplingFieldDouble *MEDCouplingFieldDouble::buildNewTimeReprFromThis(TypeOfTimeDiscretization td, bool deepCopy) const
179 MEDCouplingTimeDiscretization *tdo=timeDiscr()->buildNewTimeReprFromThis(td,deepCopy);
180 MCAuto<MEDCouplingFieldDiscretization> disc;
183 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),tdo,disc.retn()));
184 ret->setMesh(getMesh());
185 ret->setName(getName());
186 ret->setDescription(getDescription());
191 * This method converts a field on nodes (\a this) to a cell field (returned field). The convertion is a \b non \b conservative remapping !
192 * This method is useful only for users that need a fast convertion from node to cell spatial discretization. The algorithm applied is simply to attach
193 * to each cell the average of values on nodes constituting this cell.
195 * \return MEDCouplingFieldDouble* - a new instance of MEDCouplingFieldDouble. The
196 * caller is to delete this field using decrRef() as it is no more needed. The returned field will share the same mesh object object than those in \a this.
197 * \throw If \a this spatial discretization is empty or not ON_NODES.
198 * \throw If \a this is not coherent (see MEDCouplingFieldDouble::checkConsistencyLight).
200 * \warning This method is a \b non \b conservative method of remapping from node spatial discretization to cell spatial discretization.
201 * If a conservative method of interpolation is required MEDCoupling::MEDCouplingRemapper class should be used instead with "P1P0" method.
203 MEDCouplingFieldDouble *MEDCouplingFieldDouble::nodeToCellDiscretization() const
205 checkConsistencyLight();
206 TypeOfField tf(getTypeOfField());
208 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::nodeToCellDiscretization : this field is expected to be on ON_NODES !");
209 MCAuto<MEDCouplingFieldDouble> ret(clone(false));
210 MCAuto<MEDCouplingFieldDiscretizationP0> nsp(new MEDCouplingFieldDiscretizationP0);
211 ret->setDiscretization(nsp);
212 const MEDCouplingMesh *m(getMesh());//m is non empty thanks to checkConsistencyLight call
213 int nbCells(m->getNumberOfCells());
214 std::vector<DataArrayDouble *> arrs(getArrays());
215 std::size_t sz(arrs.size());
216 std::vector< MCAuto<DataArrayDouble> > outArrsSafe(sz); std::vector<DataArrayDouble *> outArrs(sz);
217 for(std::size_t j=0;j<sz;j++)
219 int nbCompo(arrs[j]->getNumberOfComponents());
220 outArrsSafe[j]=DataArrayDouble::New(); outArrsSafe[j]->alloc(nbCells,nbCompo);
221 outArrsSafe[j]->copyStringInfoFrom(*arrs[j]);
222 outArrs[j]=outArrsSafe[j];
223 double *pt(outArrsSafe[j]->getPointer());
224 const double *srcPt(arrs[j]->begin());
225 for(int i=0;i<nbCells;i++,pt+=nbCompo)
227 std::vector<int> nodeIds;
228 m->getNodeIdsOfCell(i,nodeIds);
229 std::fill(pt,pt+nbCompo,0.);
230 std::size_t nbNodesInCell(nodeIds.size());
231 for(std::size_t k=0;k<nbNodesInCell;k++)
232 std::transform(srcPt+nodeIds[k]*nbCompo,srcPt+(nodeIds[k]+1)*nbCompo,pt,pt,std::plus<double>());
234 std::transform(pt,pt+nbCompo,pt,std::bind2nd(std::multiplies<double>(),1./((double)nbNodesInCell)));
237 std::ostringstream oss; oss << "MEDCouplingFieldDouble::nodeToCellDiscretization : Cell id #" << i << " has been detected to have no nodes !";
238 throw INTERP_KERNEL::Exception(oss.str());
242 ret->setArrays(outArrs);
247 * This method converts a field on cell (\a this) to a node field (returned field). The convertion is a \b non \b conservative remapping !
248 * This method is useful only for users that need a fast convertion from cell to node spatial discretization. The algorithm applied is simply to attach
249 * to each node the average of values on cell sharing this node. If \a this lies on a mesh having orphan nodes the values applied on them will be NaN (division by 0.).
251 * \return MEDCouplingFieldDouble* - a new instance of MEDCouplingFieldDouble. The
252 * caller is to delete this field using decrRef() as it is no more needed. The returned field will share the same mesh object object than those in \a this.
253 * \throw If \a this spatial discretization is empty or not ON_CELLS.
254 * \throw If \a this is not coherent (see MEDCouplingFieldDouble::checkConsistencyLight).
256 * \warning This method is a \b non \b conservative method of remapping from cell spatial discretization to node spatial discretization.
257 * If a conservative method of interpolation is required MEDCoupling::MEDCouplingRemapper class should be used instead with "P0P1" method.
259 MEDCouplingFieldDouble *MEDCouplingFieldDouble::cellToNodeDiscretization() const
261 checkConsistencyLight();
262 TypeOfField tf(getTypeOfField());
264 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::cellToNodeDiscretization : this field is expected to be on ON_CELLS !");
265 MCAuto<MEDCouplingFieldDouble> ret(clone(false));
266 MCAuto<MEDCouplingFieldDiscretizationP1> nsp(new MEDCouplingFieldDiscretizationP1);
267 ret->setDiscretization(nsp);
268 const MEDCouplingMesh *m(getMesh());//m is non empty thanks to checkConsistencyLight call
269 MCAuto<DataArrayInt> rn(DataArrayInt::New()),rni(DataArrayInt::New());
270 m->getReverseNodalConnectivity(rn,rni);
271 MCAuto<DataArrayInt> rni2(rni->deltaShiftIndex());
272 MCAuto<DataArrayDouble> rni3(rni2->convertToDblArr()); rni2=0;
273 std::vector<DataArrayDouble *> arrs(getArrays());
274 std::size_t sz(arrs.size());
275 std::vector< MCAuto<DataArrayDouble> > outArrsSafe(sz); std::vector<DataArrayDouble *> outArrs(sz);
276 for(std::size_t j=0;j<sz;j++)
278 MCAuto<DataArrayDouble> tmp(arrs[j]->selectByTupleIdSafe(rn->begin(),rn->end()));
279 outArrsSafe[j]=(tmp->accumulatePerChunck(rni->begin(),rni->end())); tmp=0;
280 outArrsSafe[j]->divideEqual(rni3);
281 outArrsSafe[j]->copyStringInfoFrom(*arrs[j]);
282 outArrs[j]=outArrsSafe[j];
284 ret->setArrays(outArrs);
289 * Returns a string describing \a this field. The string includes info on
292 * - \ref MEDCouplingSpatialDisc "spatial discretization",
293 * - \ref MEDCouplingTemporalDisc "time discretization",
296 * - contents of data arrays.
298 * \return std::string - the string describing \a this field.
300 std::string MEDCouplingFieldDouble::advancedRepr() const
302 std::ostringstream ret;
303 ret << "FieldDouble with name : \"" << getName() << "\"\n";
304 ret << "Description of field is : \"" << getDescription() << "\"\n";
306 { ret << "FieldDouble space discretization is : " << _type->getStringRepr() << "\n"; }
308 { ret << "FieldDouble has no space discretization set !\n"; }
310 { ret << "FieldDouble time discretization is : " << timeDiscr()->getStringRepr() << "\n"; }
312 { ret << "FieldDouble has no time discretization set !\n"; }
314 ret << "FieldDouble default array has " << getArray()->getNumberOfComponents() << " components and " << getArray()->getNumberOfTuples() << " tuples.\n";
316 ret << "Mesh support information :\n__________________________\n" << _mesh->advancedRepr();
318 ret << "Mesh support information : No mesh set !\n";
319 std::vector<DataArrayDouble *> arrays;
320 timeDiscr()->getArrays(arrays);
322 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++,arrayId++)
324 ret << "Array #" << arrayId << " :\n__________\n";
326 (*iter)->reprWithoutNameStream(ret);
328 ret << "Array empty !";
334 std::string MEDCouplingFieldDouble::writeVTK(const std::string& fileName, bool isBinary) const
336 std::vector<const MEDCouplingFieldDouble *> fs(1,this);
337 return MEDCouplingFieldDouble::WriteVTK(fileName,fs,isBinary);
341 * This method states if \a this and 'other' are compatibles each other before performing any treatment.
342 * This method is good for methods like : mergeFields.
343 * This method is not very demanding compared to areStrictlyCompatible that is better for operation on fields.
345 bool MEDCouplingFieldDouble::areCompatibleForMerge(const MEDCouplingField *other) const
347 if(!MEDCouplingField::areCompatibleForMerge(other))
349 const MEDCouplingFieldDouble *otherC(dynamic_cast<const MEDCouplingFieldDouble *>(other));
352 if(!timeDiscr()->areCompatible(otherC->timeDiscr()))
358 * This method is invocated before any attempt of melding. This method is very close to areStrictlyCompatible,
359 * except that \a this and other can have different number of components.
361 bool MEDCouplingFieldDouble::areCompatibleForMeld(const MEDCouplingFieldDouble *other) const
363 if(!MEDCouplingField::areStrictlyCompatible(other))
365 if(!timeDiscr()->areCompatibleForMeld(other->timeDiscr()))
371 * Permutes values of \a this field according to a given permutation array for cells
372 * renumbering. The underlying mesh is deeply copied and its cells are also permuted.
373 * The number of cells remains the same; for that the permutation array \a old2NewBg
374 * should not contain equal ids.
375 * ** Warning, this method modifies the mesh aggreagated by \a this (by performing a deep copy ) **.
377 * \param [in] old2NewBg - the permutation array in "Old to New" mode. Its length is
378 * to be equal to \a this->getMesh()->getNumberOfCells().
379 * \param [in] check - if \c true, \a old2NewBg is transformed to a new permutation
380 * array, so that its maximal cell id to correspond to (be less than) the number
381 * of cells in mesh. This new array is then used for the renumbering. If \a
382 * check == \c false, \a old2NewBg is used as is, that is less secure as validity
383 * of ids in \a old2NewBg is not checked.
384 * \throw If the mesh is not set.
385 * \throw If the spatial discretization of \a this field is NULL.
386 * \throw If \a check == \c true and \a old2NewBg contains equal ids.
387 * \throw If mesh nature does not allow renumbering (e.g. structured mesh).
389 * \if ENABLE_EXAMPLES
390 * \ref cpp_mcfielddouble_renumberCells "Here is a C++ example".<br>
391 * \ref py_mcfielddouble_renumberCells "Here is a Python example".
394 void MEDCouplingFieldDouble::renumberCells(const int *old2NewBg, bool check)
396 renumberCellsWithoutMesh(old2NewBg,check);
397 MCAuto<MEDCouplingMesh> m=_mesh->deepCopy();
398 m->renumberCells(old2NewBg,check);
404 * Permutes values of \a this field according to a given permutation array for cells
405 * renumbering. The underlying mesh is \b not permuted.
406 * The number of cells remains the same; for that the permutation array \a old2NewBg
407 * should not contain equal ids.
408 * This method performs a part of job of renumberCells(). The reasonable use of this
409 * method is only for multi-field instances lying on the same mesh to avoid a
410 * systematic duplication and renumbering of _mesh attribute.
411 * \warning Use this method with a lot of care!
412 * \param [in] old2NewBg - the permutation array in "Old to New" mode. Its length is
413 * to be equal to \a this->getMesh()->getNumberOfCells().
414 * \param [in] check - if \c true, \a old2NewBg is transformed to a new permutation
415 * array, so that its maximal cell id to correspond to (be less than) the number
416 * of cells in mesh. This new array is then used for the renumbering. If \a
417 * check == \c false, \a old2NewBg is used as is, that is less secure as validity
418 * of ids in \a old2NewBg is not checked.
419 * \throw If the mesh is not set.
420 * \throw If the spatial discretization of \a this field is NULL.
421 * \throw If \a check == \c true and \a old2NewBg contains equal ids.
422 * \throw If mesh nature does not allow renumbering (e.g. structured mesh).
424 void MEDCouplingFieldDouble::renumberCellsWithoutMesh(const int *old2NewBg, bool check)
427 throw INTERP_KERNEL::Exception("Expecting a defined mesh to be able to operate a renumbering !");
429 throw INTERP_KERNEL::Exception("Expecting a spatial discretization to be able to operate a renumbering !");
431 _type->renumberCells(old2NewBg,check);
432 std::vector<DataArrayDouble *> arrays;
433 timeDiscr()->getArrays(arrays);
434 std::vector<DataArray *> arrays2(arrays.size()); std::copy(arrays.begin(),arrays.end(),arrays2.begin());
435 _type->renumberArraysForCell(_mesh,arrays2,old2NewBg,check);
441 * Permutes values of \a this field according to a given permutation array for node
442 * renumbering. The underlying mesh is deeply copied and its nodes are also permuted.
443 * The number of nodes can change, contrary to renumberCells().
444 * \param [in] old2NewBg - the permutation array in "Old to New" mode. Its length is
445 * to be equal to \a this->getMesh()->getNumberOfNodes().
446 * \param [in] eps - a precision used to compare field values at merged nodes. If
447 * the values differ more than \a eps, an exception is thrown.
448 * \throw If the mesh is not set.
449 * \throw If the spatial discretization of \a this field is NULL.
450 * \throw If \a check == \c true and \a old2NewBg contains equal ids.
451 * \throw If mesh nature does not allow renumbering (e.g. structured mesh).
452 * \throw If values at merged nodes deffer more than \a eps.
454 * \if ENABLE_EXAMPLES
455 * \ref cpp_mcfielddouble_renumberNodes "Here is a C++ example".<br>
456 * \ref py_mcfielddouble_renumberNodes "Here is a Python example".
459 void MEDCouplingFieldDouble::renumberNodes(const int *old2NewBg, double eps)
461 const MEDCouplingPointSet *meshC=dynamic_cast<const MEDCouplingPointSet *>(_mesh);
463 throw INTERP_KERNEL::Exception("Invalid mesh to apply renumberNodes on it !");
464 int nbOfNodes=meshC->getNumberOfNodes();
465 MCAuto<MEDCouplingPointSet> meshC2((MEDCouplingPointSet *)meshC->deepCopy());
466 int newNbOfNodes=*std::max_element(old2NewBg,old2NewBg+nbOfNodes)+1;
467 renumberNodesWithoutMesh(old2NewBg,newNbOfNodes,eps);
468 meshC2->renumberNodes(old2NewBg,newNbOfNodes);
473 * Permutes values of \a this field according to a given permutation array for nodes
474 * renumbering. The underlying mesh is \b not permuted.
475 * The number of nodes can change, contrary to renumberCells().
476 * A given epsilon specifies a threshold of error in case of two nodes are merged but
477 * the difference of values on these nodes are higher than \a eps.
478 * This method performs a part of job of renumberNodes(), excluding node renumbering
479 * in mesh. The reasonable use of this
480 * method is only for multi-field instances lying on the same mesh to avoid a
481 * systematic duplication and renumbering of _mesh attribute.
482 * \warning Use this method with a lot of care!
483 * \warning In case of an exception thrown, the contents of the data array can be
484 * partially modified until the exception occurs.
485 * \param [in] old2NewBg - the permutation array in "Old to New" mode. Its length is
486 * to be equal to \a this->getMesh()->getNumberOfNodes().
487 * \param [in] newNbOfNodes - a number of nodes in the mesh after renumbering.
488 * \param [in] eps - a precision used to compare field values at merged nodes. If
489 * the values differ more than \a eps, an exception is thrown.
490 * \throw If the mesh is not set.
491 * \throw If the spatial discretization of \a this field is NULL.
492 * \throw If values at merged nodes deffer more than \a eps.
494 void MEDCouplingFieldDouble::renumberNodesWithoutMesh(const int *old2NewBg, int newNbOfNodes, double eps)
497 throw INTERP_KERNEL::Exception("Expecting a spatial discretization to be able to operate a renumbering !");
498 std::vector<DataArrayDouble *> arrays;
499 timeDiscr()->getArrays(arrays);
500 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
502 _type->renumberValuesOnNodes(eps,old2NewBg,newNbOfNodes,*iter);
506 * Returns all tuple ids of \a this scalar field that fit the range [\a vmin,
507 * \a vmax]. This method calls DataArrayDouble::findIdsInRange().
508 * \param [in] vmin - a lower boundary of the range. Tuples with values less than \a
509 * vmin are not included in the result array.
510 * \param [in] vmax - an upper boundary of the range. Tuples with values more than \a
511 * vmax are not included in the result array.
512 * \return DataArrayInt * - a new instance of DataArrayInt holding ids of selected
513 * tuples. The caller is to delete this array using decrRef() as it is no
515 * \throw If the data array is not set.
516 * \throw If \a this->getNumberOfComponents() != 1.
518 DataArrayInt *MEDCouplingFieldDouble::findIdsInRange(double vmin, double vmax) const
521 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::findIdsInRange : no default array set !");
522 return getArray()->findIdsInRange(vmin,vmax);
525 MEDCouplingFieldInt *MEDCouplingFieldDouble::convertToIntField() const
527 MCAuto<MEDCouplingFieldTemplate> tmp(MEDCouplingFieldTemplate::New(*this));
529 double t0(getTime(t1,t2));
530 MCAuto<MEDCouplingFieldInt> ret(MEDCouplingFieldInt::New(*tmp,getTimeDiscretization()));
531 ret->setTime(t0,t1,t2);
534 MCAuto<DataArrayInt> arr(getArray()->convertToIntArr());
540 MEDCouplingFieldDouble::MEDCouplingFieldDouble(TypeOfField type, TypeOfTimeDiscretization td):MEDCouplingFieldT<double>(type,MEDCouplingTimeDiscretization::New(td))
545 * ** WARINING : This method do not deeply copy neither mesh nor spatial discretization. Only a shallow copy (reference) is done for mesh and spatial discretization ! **
547 MEDCouplingFieldDouble::MEDCouplingFieldDouble(const MEDCouplingFieldTemplate& ft, TypeOfTimeDiscretization td):MEDCouplingFieldT<double>(ft,MEDCouplingTimeDiscretization::New(td),false)
551 MEDCouplingFieldDouble::MEDCouplingFieldDouble(const MEDCouplingFieldDouble& other, bool deepCopy):MEDCouplingFieldT<double>(other,deepCopy)
555 MEDCouplingFieldDouble::MEDCouplingFieldDouble(NatureOfField n, MEDCouplingTimeDiscretization *td, MEDCouplingFieldDiscretization *type):MEDCouplingFieldT<double>(type,n,td)
560 * Accumulate values of a given component of \a this field.
561 * \param [in] compId - the index of the component of interest.
562 * \return double - a sum value of *compId*-th component.
563 * \throw If the data array is not set.
564 * \throw If \a the condition ( 0 <= \a compId < \a this->getNumberOfComponents() ) is
567 double MEDCouplingFieldDouble::accumulate(int compId) const
570 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::accumulate : no default array defined !");
571 return getArray()->accumulate(compId);
575 * Accumulates values of each component of \a this array.
576 * \param [out] res - an array of length \a this->getNumberOfComponents(), allocated
577 * by the caller, that is filled by this method with sum value for each
579 * \throw If the data array is not set.
581 void MEDCouplingFieldDouble::accumulate(double *res) const
584 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::accumulate : no default array defined !");
585 getArray()->accumulate(res);
589 * Returns the maximal value within \a this scalar field. Values of all arrays stored
590 * in \a this->_time_discr are checked.
591 * \return double - the maximal value among all values of \a this field.
592 * \throw If \a this->getNumberOfComponents() != 1
593 * \throw If the data array is not set.
594 * \throw If there is an empty data array in \a this field.
596 double MEDCouplingFieldDouble::getMaxValue() const
598 std::vector<DataArrayDouble *> arrays;
599 timeDiscr()->getArrays(arrays);
600 double ret(-std::numeric_limits<double>::max());
601 bool isExistingArr=false;
602 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
608 ret=std::max(ret,(*iter)->getMaxValue(loc));
612 throw INTERP_KERNEL::Exception("getMaxValue : No arrays defined !");
617 * Returns the maximal value and all its locations within \a this scalar field.
618 * Only the first of available data arrays is checked.
619 * \param [out] tupleIds - a new instance of DataArrayInt containg indices of
620 * tuples holding the maximal value. The caller is to delete it using
621 * decrRef() as it is no more needed.
622 * \return double - the maximal value among all values of the first array of \a this filed.
623 * \throw If \a this->getNumberOfComponents() != 1.
624 * \throw If there is an empty data array in \a this field.
626 double MEDCouplingFieldDouble::getMaxValue2(DataArrayInt*& tupleIds) const
628 std::vector<DataArrayDouble *> arrays;
629 timeDiscr()->getArrays(arrays);
630 double ret(-std::numeric_limits<double>::max());
631 bool isExistingArr=false;
633 MCAuto<DataArrayInt> ret1;
634 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
640 ret=std::max(ret,(*iter)->getMaxValue2(tmp));
641 MCAuto<DataArrayInt> tmpSafe(tmp);
642 if(!((const DataArrayInt *)ret1))
647 throw INTERP_KERNEL::Exception("getMaxValue2 : No arrays defined !");
648 tupleIds=ret1.retn();
653 * Returns the minimal value within \a this scalar field. Values of all arrays stored
654 * in \a this->_time_discr are checked.
655 * \return double - the minimal value among all values of \a this field.
656 * \throw If \a this->getNumberOfComponents() != 1
657 * \throw If the data array is not set.
658 * \throw If there is an empty data array in \a this field.
660 double MEDCouplingFieldDouble::getMinValue() const
662 std::vector<DataArrayDouble *> arrays;
663 timeDiscr()->getArrays(arrays);
664 double ret(std::numeric_limits<double>::max());
665 bool isExistingArr=false;
666 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
672 ret=std::min(ret,(*iter)->getMinValue(loc));
676 throw INTERP_KERNEL::Exception("getMinValue : No arrays defined !");
681 * Returns the minimal value and all its locations within \a this scalar field.
682 * Only the first of available data arrays is checked.
683 * \param [out] tupleIds - a new instance of DataArrayInt containg indices of
684 * tuples holding the minimal value. The caller is to delete it using
685 * decrRef() as it is no more needed.
686 * \return double - the minimal value among all values of the first array of \a this filed.
687 * \throw If \a this->getNumberOfComponents() != 1.
688 * \throw If there is an empty data array in \a this field.
690 double MEDCouplingFieldDouble::getMinValue2(DataArrayInt*& tupleIds) const
692 std::vector<DataArrayDouble *> arrays;
693 timeDiscr()->getArrays(arrays);
694 double ret(-std::numeric_limits<double>::max());
695 bool isExistingArr=false;
697 MCAuto<DataArrayInt> ret1;
698 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
704 ret=std::max(ret,(*iter)->getMinValue2(tmp));
705 MCAuto<DataArrayInt> tmpSafe(tmp);
706 if(!((const DataArrayInt *)ret1))
711 throw INTERP_KERNEL::Exception("getMinValue2 : No arrays defined !");
712 tupleIds=ret1.retn();
717 * Returns the average value of \a this scalar field.
718 * \return double - the average value over all values of the data array.
719 * \throw If \a this->getNumberOfComponents() != 1
720 * \throw If the data array is not set or it is empty.
722 double MEDCouplingFieldDouble::getAverageValue() const
725 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::getAverageValue : no default array defined !");
726 return getArray()->getAverageValue();
730 * This method returns the euclidean norm of \a this field.
732 * \sqrt{\sum_{0 \leq i < nbOfEntity}val[i]*val[i]}
734 * \throw If the data array is not set.
736 double MEDCouplingFieldDouble::norm2() const
739 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::norm2 : no default array defined !");
740 return getArray()->norm2();
744 * This method returns the max norm of \a this field.
746 * \max_{0 \leq i < nbOfEntity}{abs(val[i])}
748 * \throw If the data array is not set.
750 double MEDCouplingFieldDouble::normMax() const
753 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::normMax : no default array defined !");
754 return getArray()->normMax();
758 * Computes the weighted average of values of each component of \a this field, the weights being the
759 * values returned by buildMeasureField().
760 * \param [out] res - pointer to an array of result sum values, of size at least \a
761 * this->getNumberOfComponents(), that is to be allocated by the caller.
762 * \param [in] isWAbs - if \c true (default), \c abs() is applied to the weights computed by
763 * buildMeasureField(). It makes this method slower. If you are sure that all
764 * the cells of the underlying mesh have a correct orientation (no negative volume), you can put \a isWAbs ==
765 * \c false to speed up the method.
766 * \throw If the mesh is not set.
767 * \throw If the data array is not set.
769 void MEDCouplingFieldDouble::getWeightedAverageValue(double *res, bool isWAbs) const
772 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::getWeightedAverageValue : no default array defined !");
773 MCAuto<MEDCouplingFieldDouble> w=buildMeasureField(isWAbs);
774 double deno=w->getArray()->accumulate(0);
775 MCAuto<DataArrayDouble> arr=getArray()->deepCopy();
776 arr->multiplyEqual(w->getArray());
777 arr->accumulate(res);
778 int nCompo = getArray()->getNumberOfComponents();
779 std::transform(res,res+nCompo,res,std::bind2nd(std::multiplies<double>(),1./deno));
783 * Computes the weighted average of values of a given component of \a this field, the weights being the
784 * values returned by buildMeasureField().
785 * \param [in] compId - an index of the component of interest.
786 * \param [in] isWAbs - if \c true (default), \c abs() is applied to the weights computed by
787 * buildMeasureField(). It makes this method slower. If you are sure that all
788 * the cells of the underlying mesh have a correct orientation (no negative volume), you can put \a isWAbs ==
789 * \c false to speed up the method.
790 * \throw If the mesh is not set.
791 * \throw If the data array is not set.
792 * \throw If \a compId is not valid.
793 A valid range is ( 0 <= \a compId < \a this->getNumberOfComponents() ).
795 double MEDCouplingFieldDouble::getWeightedAverageValue(int compId, bool isWAbs) const
797 int nbComps=getArray()->getNumberOfComponents();
798 if(compId<0 || compId>=nbComps)
800 std::ostringstream oss; oss << "MEDCouplingFieldDouble::getWeightedAverageValue : Invalid compId specified : No such nb of components ! Should be in [0," << nbComps << ") !";
801 throw INTERP_KERNEL::Exception(oss.str());
803 INTERP_KERNEL::AutoPtr<double> res=new double[nbComps];
804 getWeightedAverageValue(res,isWAbs);
809 * Returns the \c normL1 of values of a given component of \a this field:
811 * \frac{\sum_{0 \leq i < nbOfEntity}|val[i]*Vol[i]|}{\sum_{0 \leq i < nbOfEntity}|Vol[i]|}
813 * \param [in] compId - an index of the component of interest.
814 * \throw If the mesh is not set.
815 * \throw If the spatial discretization of \a this field is NULL.
816 * \throw If \a compId is not valid.
817 A valid range is ( 0 <= \a compId < \a this->getNumberOfComponents() ).
819 double MEDCouplingFieldDouble::normL1(int compId) const
822 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform normL1 !");
824 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform normL1 !");
825 int nbComps=getArray()->getNumberOfComponents();
826 if(compId<0 || compId>=nbComps)
828 std::ostringstream oss; oss << "MEDCouplingFieldDouble::normL1 : Invalid compId specified : No such nb of components ! Should be in [0," << nbComps << ") !";
829 throw INTERP_KERNEL::Exception(oss.str());
831 INTERP_KERNEL::AutoPtr<double> res=new double[nbComps];
832 _type->normL1(_mesh,getArray(),res);
837 * Returns the \c normL1 of values of each component of \a this field:
839 * \frac{\sum_{0 \leq i < nbOfEntity}|val[i]*Vol[i]|}{\sum_{0 \leq i < nbOfEntity}|Vol[i]|}
841 * \param [out] res - pointer to an array of result values, of size at least \a
842 * this->getNumberOfComponents(), that is to be allocated by the caller.
843 * \throw If the mesh is not set.
844 * \throw If the spatial discretization of \a this field is NULL.
846 void MEDCouplingFieldDouble::normL1(double *res) const
849 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform normL1");
851 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform normL1 !");
852 _type->normL1(_mesh,getArray(),res);
856 * Returns the \c normL2 of values of a given component of \a this field:
858 * \sqrt{\frac{\sum_{0 \leq i < nbOfEntity}|val[i]^{2}*Vol[i]|}{\sum_{0 \leq i < nbOfEntity}|Vol[i]|}}
860 * \param [in] compId - an index of the component of interest.
861 * \throw If the mesh is not set.
862 * \throw If the spatial discretization of \a this field is NULL.
863 * \throw If \a compId is not valid.
864 A valid range is ( 0 <= \a compId < \a this->getNumberOfComponents() ).
866 double MEDCouplingFieldDouble::normL2(int compId) const
869 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform normL2");
871 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform normL2 !");
872 int nbComps=getArray()->getNumberOfComponents();
873 if(compId<0 || compId>=nbComps)
875 std::ostringstream oss; oss << "MEDCouplingFieldDouble::normL2 : Invalid compId specified : No such nb of components ! Should be in [0," << nbComps << ") !";
876 throw INTERP_KERNEL::Exception(oss.str());
878 INTERP_KERNEL::AutoPtr<double> res=new double[nbComps];
879 _type->normL2(_mesh,getArray(),res);
884 * Returns the \c normL2 of values of each component of \a this field:
886 * \sqrt{\frac{\sum_{0 \leq i < nbOfEntity}|val[i]^{2}*Vol[i]|}{\sum_{0 \leq i < nbOfEntity}|Vol[i]|}}
888 * \param [out] res - pointer to an array of result values, of size at least \a
889 * this->getNumberOfComponents(), that is to be allocated by the caller.
890 * \throw If the mesh is not set.
891 * \throw If the spatial discretization of \a this field is NULL.
893 void MEDCouplingFieldDouble::normL2(double *res) const
896 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform normL2");
898 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform normL2 !");
899 _type->normL2(_mesh,getArray(),res);
903 * Computes a sum of values of a given component of \a this field multiplied by
904 * values returned by buildMeasureField().
905 * This method is useful to check the conservativity of interpolation method.
906 * \param [in] compId - an index of the component of interest.
907 * \param [in] isWAbs - if \c true (default), \c abs() is applied to the weighs computed by
908 * buildMeasureField() that makes this method slower. If a user is sure that all
909 * cells of the underlying mesh have correct orientation, he can put \a isWAbs ==
910 * \c false that speeds up this method.
911 * \throw If the mesh is not set.
912 * \throw If the data array is not set.
913 * \throw If \a compId is not valid.
914 A valid range is ( 0 <= \a compId < \a this->getNumberOfComponents() ).
916 double MEDCouplingFieldDouble::integral(int compId, bool isWAbs) const
919 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform integral");
921 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform integral !");
922 int nbComps=getArray()->getNumberOfComponents();
923 if(compId<0 || compId>=nbComps)
925 std::ostringstream oss; oss << "MEDCouplingFieldDouble::integral : Invalid compId specified : No such nb of components ! Should be in [0," << nbComps << ") !";
926 throw INTERP_KERNEL::Exception(oss.str());
928 INTERP_KERNEL::AutoPtr<double> res=new double[nbComps];
929 _type->integral(_mesh,getArray(),isWAbs,res);
934 * Computes a sum of values of each component of \a this field multiplied by
935 * values returned by buildMeasureField().
936 * This method is useful to check the conservativity of interpolation method.
937 * \param [in] isWAbs - if \c true (default), \c abs() is applied to the weighs computed by
938 * buildMeasureField() that makes this method slower. If a user is sure that all
939 * cells of the underlying mesh have correct orientation, he can put \a isWAbs ==
940 * \c false that speeds up this method.
941 * \param [out] res - pointer to an array of result sum values, of size at least \a
942 * this->getNumberOfComponents(), that is to be allocated by the caller.
943 * \throw If the mesh is not set.
944 * \throw If the data array is not set.
945 * \throw If the spatial discretization of \a this field is NULL.
947 void MEDCouplingFieldDouble::integral(bool isWAbs, double *res) const
950 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform integral2");
952 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform integral2 !");
953 _type->integral(_mesh,getArray(),isWAbs,res);
957 * Returns a value at a given cell of a structured mesh. The cell is specified by its
959 * \param [in] i - a index of node coordinates array along X axis. The cell is
960 * located between the i-th and ( i + 1 )-th nodes along X axis.
961 * \param [in] j - a index of node coordinates array along Y axis. The cell is
962 * located between the j-th and ( j + 1 )-th nodes along Y axis.
963 * \param [in] k - a index of node coordinates array along Z axis. The cell is
964 * located between the k-th and ( k + 1 )-th nodes along Z axis.
965 * \param [out] res - pointer to an array returning a feild value, of size at least
966 * \a this->getNumberOfComponents(), that is to be allocated by the caller.
967 * \throw If the spatial discretization of \a this field is NULL.
968 * \throw If the mesh is not set.
969 * \throw If the mesh is not a structured one.
971 * \if ENABLE_EXAMPLES
972 * \ref cpp_mcfielddouble_getValueOnPos "Here is a C++ example".<br>
973 * \ref py_mcfielddouble_getValueOnPos "Here is a Python example".
976 void MEDCouplingFieldDouble::getValueOnPos(int i, int j, int k, double *res) const
978 const DataArrayDouble *arr=timeDiscr()->getArray();
980 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform getValueOnPos");
982 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getValueOnPos !");
983 _type->getValueOnPos(arr,_mesh,i,j,k,res);
987 * Returns a value of \a this at a given point using spatial discretization.
988 * \param [in] spaceLoc - the point of interest.
989 * \param [out] res - pointer to an array returning a feild value, of size at least
990 * \a this->getNumberOfComponents(), that is to be allocated by the caller.
991 * \throw If the spatial discretization of \a this field is NULL.
992 * \throw If the mesh is not set.
993 * \throw If \a spaceLoc is out of the spatial discretization.
995 * \if ENABLE_EXAMPLES
996 * \ref cpp_mcfielddouble_getValueOn "Here is a C++ example".<br>
997 * \ref py_mcfielddouble_getValueOn "Here is a Python example".
1000 void MEDCouplingFieldDouble::getValueOn(const double *spaceLoc, double *res) const
1002 const DataArrayDouble *arr=timeDiscr()->getArray();
1004 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform getValueOn");
1006 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getValueOnPos !");
1007 _type->getValueOn(arr,_mesh,spaceLoc,res);
1011 * Returns values of \a this at given points using spatial discretization.
1012 * \param [in] spaceLoc - coordinates of points of interest in full-interlace
1013 * mode. This array is to be of size ( \a nbOfPoints * \a this->getNumberOfComponents() ).
1014 * \param [in] nbOfPoints - number of points of interest.
1015 * \return DataArrayDouble * - a new instance of DataArrayDouble holding field
1016 * values relating to the input points. This array is of size \a nbOfPoints
1017 * tuples per \a this->getNumberOfComponents() components. The caller is to
1018 * delete this array using decrRef() as it is no more needed.
1019 * \throw If the spatial discretization of \a this field is NULL.
1020 * \throw If the mesh is not set.
1021 * \throw If any point in \a spaceLoc is out of the spatial discretization.
1023 * \if ENABLE_EXAMPLES
1024 * \ref cpp_mcfielddouble_getValueOnMulti "Here is a C++ example".<br>
1025 * \ref py_mcfielddouble_getValueOnMulti "Here is a Python example".
1028 DataArrayDouble *MEDCouplingFieldDouble::getValueOnMulti(const double *spaceLoc, int nbOfPoints) const
1030 const DataArrayDouble *arr=timeDiscr()->getArray();
1032 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform getValueOnMulti");
1034 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getValueOnMulti !");
1035 return _type->getValueOnMulti(arr,_mesh,spaceLoc,nbOfPoints);
1039 * Returns a value of \a this field at a given point at a given time using spatial discretization.
1040 * If the time is not covered by \a this->_time_discr, an exception is thrown.
1041 * \param [in] spaceLoc - the point of interest.
1042 * \param [in] time - the time of interest.
1043 * \param [out] res - pointer to an array returning a feild value, of size at least
1044 * \a this->getNumberOfComponents(), that is to be allocated by the caller.
1045 * \throw If the spatial discretization of \a this field is NULL.
1046 * \throw If the mesh is not set.
1047 * \throw If \a spaceLoc is out of the spatial discretization.
1048 * \throw If \a time is not covered by \a this->_time_discr.
1050 * \if ENABLE_EXAMPLES
1051 * \ref cpp_mcfielddouble_getValueOn_time "Here is a C++ example".<br>
1052 * \ref py_mcfielddouble_getValueOn_time "Here is a Python example".
1055 void MEDCouplingFieldDouble::getValueOn(const double *spaceLoc, double time, double *res) const
1057 std::vector< const DataArrayDouble *> arrs=timeDiscr()->getArraysForTime(time);
1059 throw INTERP_KERNEL::Exception("No mesh underlying this field to perform getValueOn");
1061 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getValueOn !");
1062 std::vector<double> res2;
1063 for(std::vector< const DataArrayDouble *>::const_iterator iter=arrs.begin();iter!=arrs.end();iter++)
1065 int sz=(int)res2.size();
1066 res2.resize(sz+(*iter)->getNumberOfComponents());
1067 _type->getValueOn(*iter,_mesh,spaceLoc,&res2[sz]);
1069 timeDiscr()->getValueForTime(time,res2,res);
1073 * Apply a linear function to a given component of \a this field, so that
1074 * a component value <em>(x)</em> becomes \f$ a * x + b \f$.
1075 * \param [in] a - the first coefficient of the function.
1076 * \param [in] b - the second coefficient of the function.
1077 * \param [in] compoId - the index of component to modify.
1078 * \throw If the data array(s) is(are) not set.
1080 void MEDCouplingFieldDouble::applyLin(double a, double b, int compoId)
1082 timeDiscr()->applyLin(a,b,compoId);
1086 * Apply a linear function to all components of \a this field, so that
1087 * values <em>(x)</em> becomes \f$ a * x + b \f$.
1088 * \param [in] a - the first coefficient of the function.
1089 * \param [in] b - the second coefficient of the function.
1090 * \throw If the data array(s) is(are) not set.
1092 void MEDCouplingFieldDouble::applyLin(double a, double b)
1094 timeDiscr()->applyLin(a,b);
1098 * This method sets \a this to a uniform scalar field with one component.
1099 * All tuples will have the same value 'value'.
1100 * An exception is thrown if no underlying mesh is defined.
1102 MEDCouplingFieldDouble &MEDCouplingFieldDouble::operator=(double value)
1105 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::operator= : no mesh defined !");
1107 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform operator = !");
1108 int nbOfTuple=_type->getNumberOfTuples(_mesh);
1109 timeDiscr()->setOrCreateUniformValueOnAllComponents(nbOfTuple,value);
1114 * Creates data array(s) of \a this field by using a C function for value generation.
1115 * \param [in] nbOfComp - the number of components for \a this field to have.
1116 * \param [in] func - the function used to compute values of \a this field.
1117 * This function is to compute a field value basing on coordinates of value
1119 * \throw If the mesh is not set.
1120 * \throw If \a func returns \c false.
1121 * \throw If the spatial discretization of \a this field is NULL.
1123 * \if ENABLE_EXAMPLES
1124 * \ref cpp_mcfielddouble_fillFromAnalytic_c_func "Here is a C++ example".
1127 void MEDCouplingFieldDouble::fillFromAnalytic(int nbOfComp, FunctionToEvaluate func)
1130 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::fillFromAnalytic : no mesh defined !");
1132 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform fillFromAnalytic !");
1133 MCAuto<DataArrayDouble> loc=_type->getLocalizationOfDiscValues(_mesh);
1134 timeDiscr()->fillFromAnalytic(loc,nbOfComp,func);
1138 * Creates data array(s) of \a this field by using a function for value generation.<br>
1139 * The function is applied to coordinates of value location points. For example, if
1140 * \a this field is on cells, the function is applied to cell barycenters.
1141 * For more info on supported expressions that can be used in the function, see \ref
1142 * MEDCouplingArrayApplyFuncExpr. <br>
1143 * The function can include arbitrary named variables
1144 * (e.g. "x","y" or "va44") to refer to components of point coordinates. Names of
1145 * variables are sorted in \b alphabetical \b order to associate a variable name with a
1146 * component. For example, in the expression "2*x+z", "x" stands for the component #0
1147 * and "z" stands for the component #1 (\b not #2)!<br>
1148 * In a general case, a value resulting from the function evaluation is assigned to all
1149 * components of a field value. But there is a possibility to have its own expression for
1150 * each component within one function. For this purpose, there are predefined variable
1151 * names (IVec, JVec, KVec, LVec etc) each dedicated to a certain component (IVec, to
1152 * the component #0 etc). A factor of such a variable is added to the
1153 * corresponding component only.<br>
1154 * For example, \a nbOfComp == 4, coordinates of a 3D point are (1.,3.,7.), then
1155 * - "2*x + z" produces (5.,5.,5.,5.)
1156 * - "2*x + 0*y + z" produces (9.,9.,9.,9.)
1157 * - "2*x*IVec + (x+z)*LVec" produces (2.,0.,0.,4.)
1158 * - "2*y*IVec + z*KVec + x" produces (7.,1.,1.,4.)
1160 * \param [in] nbOfComp - the number of components for \a this field to have.
1161 * \param [in] func - the function used to compute values of \a this field.
1162 * This function is used to compute a field value basing on coordinates of value
1163 * location point. For example, if \a this field is on cells, the function
1164 * is applied to cell barycenters.
1165 * \throw If the mesh is not set.
1166 * \throw If the spatial discretization of \a this field is NULL.
1167 * \throw If computing \a func fails.
1169 * \if ENABLE_EXAMPLES
1170 * \ref cpp_mcfielddouble_fillFromAnalytic "Here is a C++ example".<br>
1171 * \ref py_mcfielddouble_fillFromAnalytic "Here is a Python example".
1174 void MEDCouplingFieldDouble::fillFromAnalytic(int nbOfComp, const std::string& func)
1177 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::fillFromAnalytic : no mesh defined !");
1179 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform fillFromAnalytic !");
1180 MCAuto<DataArrayDouble> loc=_type->getLocalizationOfDiscValues(_mesh);
1181 timeDiscr()->fillFromAnalytic(loc,nbOfComp,func);
1185 * Creates data array(s) of \a this field by using a function for value generation.<br>
1186 * The function is applied to coordinates of value location points. For example, if
1187 * \a this field is on cells, the function is applied to cell barycenters.<br>
1188 * This method differs from
1189 * \ref MEDCoupling::MEDCouplingFieldDouble::fillFromAnalytic(int nbOfComp, const std::string& func) "fillFromAnalytic()"
1190 * by the way how variable
1191 * names, used in the function, are associated with components of coordinates of field
1192 * location points; here, a variable name corresponding to a component is retrieved from
1193 * a corresponding node coordinates array (where it is set via
1194 * DataArrayDouble::setInfoOnComponent()).<br>
1195 * For more info on supported expressions that can be used in the function, see \ref
1196 * MEDCouplingArrayApplyFuncExpr. <br>
1197 * In a general case, a value resulting from the function evaluation is assigned to all
1198 * components of a field value. But there is a possibility to have its own expression for
1199 * each component within one function. For this purpose, there are predefined variable
1200 * names (IVec, JVec, KVec, LVec etc) each dedicated to a certain component (IVec, to
1201 * the component #0 etc). A factor of such a variable is added to the
1202 * corresponding component only.<br>
1203 * For example, \a nbOfComp == 4, names of spatial components are "x", "y" and "z",
1204 * coordinates of a 3D point are (1.,3.,7.), then
1205 * - "2*x + z" produces (9.,9.,9.,9.)
1206 * - "2*x*IVec + (x+z)*LVec" produces (2.,0.,0.,8.)
1207 * - "2*y*IVec + z*KVec + x" produces (7.,1.,1.,8.)
1209 * \param [in] nbOfComp - the number of components for \a this field to have.
1210 * \param [in] func - the function used to compute values of \a this field.
1211 * This function is used to compute a field value basing on coordinates of value
1212 * location point. For example, if \a this field is on cells, the function
1213 * is applied to cell barycenters.
1214 * \throw If the mesh is not set.
1215 * \throw If the spatial discretization of \a this field is NULL.
1216 * \throw If computing \a func fails.
1218 * \if ENABLE_EXAMPLES
1219 * \ref cpp_mcfielddouble_fillFromAnalytic2 "Here is a C++ example".<br>
1220 * \ref py_mcfielddouble_fillFromAnalytic2 "Here is a Python example".
1223 void MEDCouplingFieldDouble::fillFromAnalyticCompo(int nbOfComp, const std::string& func)
1226 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::fillFromAnalyticCompo : no mesh defined !");
1228 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform fillFromAnalyticCompo !");
1229 MCAuto<DataArrayDouble> loc=_type->getLocalizationOfDiscValues(_mesh);
1230 timeDiscr()->fillFromAnalyticCompo(loc,nbOfComp,func);
1234 * Creates data array(s) of \a this field by using a function for value generation.<br>
1235 * The function is applied to coordinates of value location points. For example, if
1236 * \a this field is on cells, the function is applied to cell barycenters.<br>
1237 * This method differs from
1238 * \ref MEDCoupling::MEDCouplingFieldDouble::fillFromAnalytic(int nbOfComp, const std::string& func) "fillFromAnalytic()"
1239 * by the way how variable
1240 * names, used in the function, are associated with components of coordinates of field
1241 * location points; here, a component index of a variable is defined by a
1242 * rank of the variable within the input array \a varsOrder.<br>
1243 * For more info on supported expressions that can be used in the function, see \ref
1244 * MEDCouplingArrayApplyFuncExpr.
1245 * In a general case, a value resulting from the function evaluation is assigned to all
1246 * components of a field value. But there is a possibility to have its own expression for
1247 * each component within one function. For this purpose, there are predefined variable
1248 * names (IVec, JVec, KVec, LVec etc) each dedicated to a certain component (IVec, to
1249 * the component #0 etc). A factor of such a variable is added to the
1250 * corresponding component only.<br>
1251 * For example, \a nbOfComp == 4, names of
1252 * spatial components are given in \a varsOrder: ["x", "y","z"], coordinates of a
1253 * 3D point are (1.,3.,7.), then
1254 * - "2*x + z" produces (9.,9.,9.,9.)
1255 * - "2*x*IVec + (x+z)*LVec" produces (2.,0.,0.,8.)
1256 * - "2*y*IVec + z*KVec + x" produces (7.,1.,1.,8.)
1258 * \param [in] nbOfComp - the number of components for \a this field to have.
1259 * \param [in] func - the function used to compute values of \a this field.
1260 * This function is used to compute a field value basing on coordinates of value
1261 * location point. For example, if \a this field is on cells, the function
1262 * is applied to cell barycenters.
1263 * \throw If the mesh is not set.
1264 * \throw If the spatial discretization of \a this field is NULL.
1265 * \throw If computing \a func fails.
1267 * \if ENABLE_EXAMPLES
1268 * \ref cpp_mcfielddouble_fillFromAnalytic3 "Here is a C++ example".<br>
1269 * \ref py_mcfielddouble_fillFromAnalytic3 "Here is a Python example".
1272 void MEDCouplingFieldDouble::fillFromAnalyticNamedCompo(int nbOfComp, const std::vector<std::string>& varsOrder, const std::string& func)
1275 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::fillFromAnalyticCompo : no mesh defined !");
1277 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform fillFromAnalyticNamedCompo !");
1278 MCAuto<DataArrayDouble> loc=_type->getLocalizationOfDiscValues(_mesh);
1279 timeDiscr()->fillFromAnalyticNamedCompo(loc,nbOfComp,varsOrder,func);
1283 * Modifies values of \a this field by applying a C function to each tuple of all
1285 * \param [in] nbOfComp - the number of components for \a this field to have.
1286 * \param [in] func - the function used to compute values of \a this field.
1287 * This function is to compute a field value basing on a current field value.
1288 * \throw If \a func returns \c false.
1290 * \if ENABLE_EXAMPLES
1291 * \ref cpp_mcfielddouble_applyFunc_c_func "Here is a C++ example".
1294 void MEDCouplingFieldDouble::applyFunc(int nbOfComp, FunctionToEvaluate func)
1296 timeDiscr()->applyFunc(nbOfComp,func);
1300 * Fill \a this field with a given value.<br>
1301 * This method is a specialization of other overloaded methods. When \a nbOfComp == 1
1302 * this method is equivalent to MEDCoupling::MEDCouplingFieldDouble::operator=().
1303 * \param [in] nbOfComp - the number of components for \a this field to have.
1304 * \param [in] val - the value to assign to every atomic value of \a this field.
1305 * \throw If the spatial discretization of \a this field is NULL.
1306 * \throw If the mesh is not set.
1308 * \if ENABLE_EXAMPLES
1309 * \ref cpp_mcfielddouble_applyFunc_val "Here is a C++ example".<br>
1310 * \ref py_mcfielddouble_applyFunc_val "Here is a Python example".
1313 void MEDCouplingFieldDouble::applyFunc(int nbOfComp, double val)
1316 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::applyFunc : no mesh defined !");
1318 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform applyFunc !");
1319 int nbOfTuple=_type->getNumberOfTuples(_mesh);
1320 timeDiscr()->setUniformValue(nbOfTuple,nbOfComp,val);
1324 * Modifies values of \a this field by applying a function to each tuple of all
1326 * For more info on supported expressions that can be used in the function, see \ref
1327 * MEDCouplingArrayApplyFuncExpr. <br>
1328 * The function can include arbitrary named variables
1329 * (e.g. "x","y" or "va44") to refer to components of a field value. Names of
1330 * variables are sorted in \b alphabetical \b order to associate a variable name with a
1331 * component. For example, in the expression "2*x+z", "x" stands for the component #0
1332 * and "z" stands for the component #1 (\b not #2)!<br>
1333 * In a general case, a value resulting from the function evaluation is assigned to all
1334 * components of a field value. But there is a possibility to have its own expression for
1335 * each component within one function. For this purpose, there are predefined variable
1336 * names (IVec, JVec, KVec, LVec etc) each dedicated to a certain component (IVec, to
1337 * the component #0 etc). A factor of such a variable is added to the
1338 * corresponding component only.<br>
1339 * For example, \a nbOfComp == 4, components of a field value are (1.,3.,7.), then
1340 * - "2*x + z" produces (5.,5.,5.,5.)
1341 * - "2*x + 0*y + z" produces (9.,9.,9.,9.)
1342 * - "2*x*IVec + (x+z)*LVec" produces (2.,0.,0.,4.)
1343 * - "2*y*IVec + z*KVec + x" produces (7.,1.,1.,4.)
1345 * \param [in] nbOfComp - the number of components for \a this field to have.
1346 * \param [in] func - the function used to compute values of \a this field.
1347 * This function is to compute a field value basing on a current field value.
1348 * \throw If computing \a func fails.
1350 * \if ENABLE_EXAMPLES
1351 * \ref cpp_mcfielddouble_applyFunc "Here is a C++ example".<br>
1352 * \ref py_mcfielddouble_applyFunc "Here is a Python example".
1355 void MEDCouplingFieldDouble::applyFunc(int nbOfComp, const std::string& func)
1357 timeDiscr()->applyFunc(nbOfComp,func);
1362 * Modifies values of \a this field by applying a function to each tuple of all
1364 * For more info on supported expressions that can be used in the function, see \ref
1365 * MEDCouplingArrayApplyFuncExpr. <br>
1366 * This method differs from
1367 * \ref MEDCoupling::MEDCouplingFieldDouble::applyFunc(int nbOfComp, const std::string& func) "applyFunc()"
1368 * by the way how variable
1369 * names, used in the function, are associated with components of field values;
1370 * here, a variable name corresponding to a component is retrieved from
1371 * component information of an array (where it is set via
1372 * DataArrayDouble::setInfoOnComponent()).<br>
1373 * In a general case, a value resulting from the function evaluation is assigned to all
1374 * components of a field value. But there is a possibility to have its own expression for
1375 * each component within one function. For this purpose, there are predefined variable
1376 * names (IVec, JVec, KVec, LVec etc) each dedicated to a certain component (IVec, to
1377 * the component #0 etc). A factor of such a variable is added to the
1378 * corresponding component only.<br>
1379 * For example, \a nbOfComp == 4, components of a field value are (1.,3.,7.), then
1380 * - "2*x + z" produces (5.,5.,5.,5.)
1381 * - "2*x + 0*y + z" produces (9.,9.,9.,9.)
1382 * - "2*x*IVec + (x+z)*LVec" produces (2.,0.,0.,4.)
1383 * - "2*y*IVec + z*KVec + x" produces (7.,1.,1.,4.)
1385 * \param [in] nbOfComp - the number of components for \a this field to have.
1386 * \param [in] func - the function used to compute values of \a this field.
1387 * This function is to compute a new field value basing on a current field value.
1388 * \throw If computing \a func fails.
1390 * \if ENABLE_EXAMPLES
1391 * \ref cpp_mcfielddouble_applyFunc2 "Here is a C++ example".<br>
1392 * \ref py_mcfielddouble_applyFunc2 "Here is a Python example".
1395 void MEDCouplingFieldDouble::applyFuncCompo(int nbOfComp, const std::string& func)
1397 timeDiscr()->applyFuncCompo(nbOfComp,func);
1401 * Modifies values of \a this field by applying a function to each tuple of all
1403 * This method differs from
1404 * \ref MEDCoupling::MEDCouplingFieldDouble::applyFunc(int nbOfComp, const std::string& func) "applyFunc()"
1405 * by the way how variable
1406 * names, used in the function, are associated with components of field values;
1407 * here, a component index of a variable is defined by a
1408 * rank of the variable within the input array \a varsOrder.<br>
1409 * For more info on supported expressions that can be used in the function, see \ref
1410 * MEDCouplingArrayApplyFuncExpr.
1411 * In a general case, a value resulting from the function evaluation is assigned to all
1412 * components of a field value. But there is a possibility to have its own expression for
1413 * each component within one function. For this purpose, there are predefined variable
1414 * names (IVec, JVec, KVec, LVec etc) each dedicated to a certain component (IVec, to
1415 * the component #0 etc). A factor of such a variable is added to the
1416 * corresponding component only.<br>
1417 * For example, \a nbOfComp == 4, names of
1418 * components are given in \a varsOrder: ["x", "y","z"], components of a
1419 * 3D vector are (1.,3.,7.), then
1420 * - "2*x + z" produces (9.,9.,9.,9.)
1421 * - "2*x*IVec + (x+z)*LVec" produces (2.,0.,0.,8.)
1422 * - "2*y*IVec + z*KVec + x" produces (7.,1.,1.,8.)
1424 * \param [in] nbOfComp - the number of components for \a this field to have.
1425 * \param [in] func - the function used to compute values of \a this field.
1426 * This function is to compute a new field value basing on a current field value.
1427 * \throw If computing \a func fails.
1429 * \if ENABLE_EXAMPLES
1430 * \ref cpp_mcfielddouble_applyFunc3 "Here is a C++ example".<br>
1431 * \ref py_mcfielddouble_applyFunc3 "Here is a Python example".
1434 void MEDCouplingFieldDouble::applyFuncNamedCompo(int nbOfComp, const std::vector<std::string>& varsOrder, const std::string& func)
1436 timeDiscr()->applyFuncNamedCompo(nbOfComp,varsOrder,func);
1440 * Modifies values of \a this field by applying a function to each atomic value of all
1441 * data arrays. The function computes a new single value basing on an old single value.
1442 * For more info on supported expressions that can be used in the function, see \ref
1443 * MEDCouplingArrayApplyFuncExpr. <br>
1444 * The function can include **only one** arbitrary named variable
1445 * (e.g. "x","y" or "va44") to refer to a field atomic value. <br>
1446 * In a general case, a value resulting from the function evaluation is assigned to
1447 * a single field value. But there is a possibility to have its own expression for
1448 * each component within one function. For this purpose, there are predefined variable
1449 * names (IVec, JVec, KVec, LVec etc) each dedicated to a certain component (IVec, to
1450 * the component #0 etc). A factor of such a variable is added to the
1451 * corresponding component only.<br>
1452 * For example, components of a field value are (1.,3.,7.), then
1453 * - "2*x - 1" produces (1.,5.,13.)
1454 * - "2*x*IVec + (x+3)*KVec" produces (2.,0.,10.)
1455 * - "2*x*IVec + (x+3)*KVec + 1" produces (3.,1.,11.)
1457 * \param [in] func - the function used to compute values of \a this field.
1458 * This function is to compute a field value basing on a current field value.
1459 * \throw If computing \a func fails.
1461 * \if ENABLE_EXAMPLES
1462 * \ref cpp_mcfielddouble_applyFunc_same_nb_comp "Here is a C++ example".<br>
1463 * \ref py_mcfielddouble_applyFunc_same_nb_comp "Here is a Python example".
1466 void MEDCouplingFieldDouble::applyFunc(const std::string& func)
1468 timeDiscr()->applyFunc(func);
1472 * Applyies the function specified by the string repr 'func' on each tuples on all arrays contained in _time_discr.
1473 * The field will contain exactly the same number of components after the call.
1474 * Use is not warranted for the moment !
1476 void MEDCouplingFieldDouble::applyFuncFast32(const std::string& func)
1478 timeDiscr()->applyFuncFast32(func);
1482 * Applyies the function specified by the string repr 'func' on each tuples on all arrays contained in _time_discr.
1483 * The field will contain exactly the same number of components after the call.
1484 * Use is not warranted for the moment !
1486 void MEDCouplingFieldDouble::applyFuncFast64(const std::string& func)
1488 timeDiscr()->applyFuncFast64(func);
1492 * Returns number of components in the data array. For more info on the data arrays,
1494 * \return int - the number of components in the data array.
1495 * \throw If the data array is not set.
1497 std::size_t MEDCouplingFieldDouble::getNumberOfComponents() const
1500 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::getNumberOfComponents : No array specified !");
1501 return getArray()->getNumberOfComponents();
1505 * Use MEDCouplingField::getNumberOfTuplesExpected instead of this method. This method will be removed soon, because it is
1506 * confusing compared to getNumberOfComponents() and getNumberOfValues() behaviour.
1508 * Returns number of tuples in \a this field, that depends on
1509 * - the number of entities in the underlying mesh
1510 * - \ref MEDCouplingSpatialDisc "spatial discretization" of \a this field (e.g. number
1511 * of Gauss points if \a this->getTypeOfField() ==
1512 * \ref MEDCoupling::ON_GAUSS_PT "ON_GAUSS_PT").
1514 * The returned value does \b not \b depend on the number of tuples in the data array
1515 * (which has to be equal to the returned value), \b contrary to
1516 * getNumberOfComponents() and getNumberOfValues() that retrieve information from the
1517 * data array (Sorry, it is confusing !).
1518 * So \b this \b method \b behaves \b exactly \b as MEDCouplingField::getNumberOfTuplesExpected \b method.
1520 * \warning No checkConsistencyLight() is done here.
1521 * For more info on the data arrays, see \ref arrays.
1522 * \return int - the number of tuples.
1523 * \throw If the mesh is not set.
1524 * \throw If the spatial discretization of \a this field is NULL.
1525 * \throw If the spatial discretization is not fully defined.
1526 * \sa MEDCouplingField::getNumberOfTuplesExpected
1528 std::size_t MEDCouplingFieldDouble::getNumberOfTuples() const
1531 throw INTERP_KERNEL::Exception("Impossible to retrieve number of tuples because no mesh specified !");
1533 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getNumberOfTuples !");
1534 return _type->getNumberOfTuples(_mesh);
1538 * Returns number of atomic double values in the data array of \a this field.
1539 * For more info on the data arrays, see \ref arrays.
1540 * \return int - (number of tuples) * (number of components) of the
1542 * \throw If the data array is not set.
1544 std::size_t MEDCouplingFieldDouble::getNumberOfValues() const
1547 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::getNumberOfValues : No array specified !");
1548 return getArray()->getNbOfElems();
1552 * Sets own modification time by the most recently modified element of data (the mesh,
1553 * the data array etc). For more info, see \ref MEDCouplingTimeLabelPage.
1555 void MEDCouplingFieldDouble::updateTime() const
1557 MEDCouplingField::updateTime();
1558 updateTimeWith(*timeDiscr());
1561 std::size_t MEDCouplingFieldDouble::getHeapMemorySizeWithoutChildren() const
1563 return MEDCouplingField::getHeapMemorySizeWithoutChildren();
1566 std::vector<const BigMemoryObject *> MEDCouplingFieldDouble::getDirectChildrenWithNull() const
1568 std::vector<const BigMemoryObject *> ret(MEDCouplingField::getDirectChildrenWithNull());
1571 std::vector<const BigMemoryObject *> ret2(timeDiscr()->getDirectChildrenWithNull());
1572 ret.insert(ret.end(),ret2.begin(),ret2.end());
1578 * Returns a value of \a this field of type either
1579 * \ref MEDCoupling::ON_GAUSS_PT "ON_GAUSS_PT" or
1580 * \ref MEDCoupling::ON_GAUSS_NE "ON_GAUSS_NE".
1581 * \param [in] cellId - an id of cell of interest.
1582 * \param [in] nodeIdInCell - a node index within the cell.
1583 * \param [in] compoId - an index of component.
1584 * \return double - the field value corresponding to the specified parameters.
1585 * \throw If the data array is not set.
1586 * \throw If the mesh is not set.
1587 * \throw If the spatial discretization of \a this field is NULL.
1588 * \throw If \a this field if of type other than
1589 * \ref MEDCoupling::ON_GAUSS_PT "ON_GAUSS_PT" or
1590 * \ref MEDCoupling::ON_GAUSS_NE "ON_GAUSS_NE".
1592 double MEDCouplingFieldDouble::getIJK(int cellId, int nodeIdInCell, int compoId) const
1595 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getIJK !");
1596 return _type->getIJK(_mesh,getArray(),cellId,nodeIdInCell,compoId);
1600 * Sets the data array.
1601 * \param [in] array - the data array holding values of \a this field. It's size
1602 * should correspond to the mesh and
1603 * \ref MEDCouplingSpatialDisc "spatial discretization" of \a this field
1604 * (see getNumberOfTuples()), but this size is not checked here.
1606 //void MEDCouplingFieldDouble::setArray(DataArrayDouble *array)
1609 * Sets the data array holding values corresponding to an end of a time interval
1610 * for which \a this field is defined.
1611 * \param [in] array - the data array holding values of \a this field. It's size
1612 * should correspond to the mesh and
1613 * \ref MEDCouplingSpatialDisc "spatial discretization" of \a this field
1614 * (see getNumberOfTuples()), but this size is not checked here.
1616 //void MEDCouplingFieldDouble::setEndArray(DataArrayDouble *array)
1619 * Sets all data arrays needed to define the field values.
1620 * \param [in] arrs - a vector of DataArrayDouble's holding values of \a this
1621 * field. Size of each array should correspond to the mesh and
1622 * \ref MEDCouplingSpatialDisc "spatial discretization" of \a this field
1623 * (see getNumberOfTuples()), but this size is not checked here.
1624 * \throw If number of arrays in \a arrs does not correspond to type of
1625 * \ref MEDCouplingTemporalDisc "temporal discretization" of \a this field.
1627 //void MEDCouplingFieldDouble::setArrays(const std::vector<DataArrayDouble *>& arrs)
1629 void MEDCouplingFieldDouble::getTinySerializationStrInformation(std::vector<std::string>& tinyInfo) const
1632 timeDiscr()->getTinySerializationStrInformation(tinyInfo);
1633 tinyInfo.push_back(_name);
1634 tinyInfo.push_back(_desc);
1635 tinyInfo.push_back(getTimeUnit());
1639 * This method retrieves some critical values to resize and prepare remote instance.
1640 * The first two elements returned in tinyInfo correspond to the parameters to give in constructor.
1641 * @param tinyInfo out parameter resized correctly after the call. The length of this vector is tiny.
1643 void MEDCouplingFieldDouble::getTinySerializationIntInformation(std::vector<int>& tinyInfo) const
1646 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getTinySerializationIntInformation !");
1648 tinyInfo.push_back((int)_type->getEnum());
1649 tinyInfo.push_back((int)timeDiscr()->getEnum());
1650 tinyInfo.push_back((int)_nature);
1651 timeDiscr()->getTinySerializationIntInformation(tinyInfo);
1652 std::vector<int> tinyInfo2;
1653 _type->getTinySerializationIntInformation(tinyInfo2);
1654 tinyInfo.insert(tinyInfo.end(),tinyInfo2.begin(),tinyInfo2.end());
1655 tinyInfo.push_back((int)tinyInfo2.size());
1659 * This method retrieves some critical values to resize and prepare remote instance.
1660 * @param tinyInfo out parameter resized correctly after the call. The length of this vector is tiny.
1662 void MEDCouplingFieldDouble::getTinySerializationDbleInformation(std::vector<double>& tinyInfo) const
1665 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform getTinySerializationDbleInformation !");
1667 timeDiscr()->getTinySerializationDbleInformation(tinyInfo);
1668 std::vector<double> tinyInfo2;
1669 _type->getTinySerializationDbleInformation(tinyInfo2);
1670 tinyInfo.insert(tinyInfo.end(),tinyInfo2.begin(),tinyInfo2.end());
1671 tinyInfo.push_back((int)tinyInfo2.size());//very bad, lack of time to improve it
1675 * This method has to be called to the new instance filled by CORBA, MPI, File...
1676 * @param tinyInfoI is the value retrieves from distant result of getTinySerializationIntInformation on source instance to be copied.
1677 * @param dataInt out parameter. If not null the pointer is already owned by \a this after the call of this method. In this case no decrRef must be applied.
1678 * @param arrays out parameter is a vector resized to the right size. The pointers in the vector is already owned by \a this after the call of this method.
1679 * No decrRef must be applied to every instances in returned vector.
1680 * \sa checkForUnserialization
1682 void MEDCouplingFieldDouble::resizeForUnserialization(const std::vector<int>& tinyInfoI, DataArrayInt *&dataInt, std::vector<DataArrayDouble *>& arrays)
1685 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform resizeForUnserialization !");
1687 std::vector<int> tinyInfoITmp(tinyInfoI);
1688 int sz=tinyInfoITmp.back();
1689 tinyInfoITmp.pop_back();
1690 std::vector<int> tinyInfoITmp2(tinyInfoITmp.begin(),tinyInfoITmp.end()-sz);
1691 std::vector<int> tinyInfoI2(tinyInfoITmp2.begin()+3,tinyInfoITmp2.end());
1692 timeDiscr()->resizeForUnserialization(tinyInfoI2,arrays);
1693 std::vector<int> tinyInfoITmp3(tinyInfoITmp.end()-sz,tinyInfoITmp.end());
1694 _type->resizeForUnserialization(tinyInfoITmp3,dataInt);
1698 * This method is extremely close to resizeForUnserialization except that here the arrays in \a dataInt and in \a arrays are attached in \a this
1699 * after having checked that size is correct. This method is used in python pickeling context to avoid copy of data.
1700 * \sa resizeForUnserialization
1702 void MEDCouplingFieldDouble::checkForUnserialization(const std::vector<int>& tinyInfoI, const DataArrayInt *dataInt, const std::vector<DataArrayDouble *>& arrays)
1705 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform resizeForUnserialization !");
1706 std::vector<int> tinyInfoITmp(tinyInfoI);
1707 int sz=tinyInfoITmp.back();
1708 tinyInfoITmp.pop_back();
1709 std::vector<int> tinyInfoITmp2(tinyInfoITmp.begin(),tinyInfoITmp.end()-sz);
1710 std::vector<int> tinyInfoI2(tinyInfoITmp2.begin()+3,tinyInfoITmp2.end());
1711 timeDiscr()->checkForUnserialization(tinyInfoI2,arrays);
1712 std::vector<int> tinyInfoITmp3(tinyInfoITmp.end()-sz,tinyInfoITmp.end());
1713 _type->checkForUnserialization(tinyInfoITmp3,dataInt);
1716 void MEDCouplingFieldDouble::finishUnserialization(const std::vector<int>& tinyInfoI, const std::vector<double>& tinyInfoD, const std::vector<std::string>& tinyInfoS)
1719 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform finishUnserialization !");
1720 std::vector<int> tinyInfoI2(tinyInfoI.begin()+3,tinyInfoI.end());
1722 std::vector<double> tmp(tinyInfoD);
1723 int sz=(int)tinyInfoD.back();//very bad, lack of time to improve it
1725 std::vector<double> tmp1(tmp.begin(),tmp.end()-sz);
1726 std::vector<double> tmp2(tmp.end()-sz,tmp.end());
1728 timeDiscr()->finishUnserialization(tinyInfoI2,tmp1,tinyInfoS);
1729 _nature=(NatureOfField)tinyInfoI[2];
1730 _type->finishUnserialization(tmp2);
1731 int nbOfElemS=(int)tinyInfoS.size();
1732 _name=tinyInfoS[nbOfElemS-3];
1733 _desc=tinyInfoS[nbOfElemS-2];
1734 setTimeUnit(tinyInfoS[nbOfElemS-1]);
1738 * Contrary to MEDCouplingPointSet class the returned arrays are \b not the responsabilities of the caller.
1739 * The values returned must be consulted only in readonly mode.
1741 void MEDCouplingFieldDouble::serialize(DataArrayInt *&dataInt, std::vector<DataArrayDouble *>& arrays) const
1744 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform serialize !");
1745 timeDiscr()->getArrays(arrays);
1746 _type->getSerializationIntArray(dataInt);
1750 * Tries to set an \a other mesh as the support of \a this field. An attempt fails, if
1751 * a current and the \a other meshes are different with use of specified equality
1752 * criteria, and then an exception is thrown.
1753 * \param [in] other - the mesh to use as the field support if this mesh can be
1754 * considered equal to the current mesh.
1755 * \param [in] levOfCheck - defines equality criteria used for mesh comparison. For
1756 * it's meaning explanation, see MEDCouplingMesh::checkGeoEquivalWith() which
1757 * is used for mesh comparison.
1758 * \param [in] precOnMesh - a precision used to compare nodes of the two meshes.
1759 * It is used as \a prec parameter of MEDCouplingMesh::checkGeoEquivalWith().
1760 * \param [in] eps - a precision used at node renumbering (if needed) to compare field
1761 * values at merged nodes. If the values differ more than \a eps, an
1762 * exception is thrown.
1763 * \throw If the mesh is not set.
1764 * \throw If \a other == NULL.
1765 * \throw If any of the meshes is not well defined.
1766 * \throw If the two meshes do not match.
1767 * \throw If field values at merged nodes (if any) deffer more than \a eps.
1769 * \if ENABLE_EXAMPLES
1770 * \ref cpp_mcfielddouble_changeUnderlyingMesh "Here is a C++ example".<br>
1771 * \ref py_mcfielddouble_changeUnderlyingMesh "Here is a Python example".
1774 void MEDCouplingFieldDouble::changeUnderlyingMesh(const MEDCouplingMesh *other, int levOfCheck, double precOnMesh, double eps)
1776 if(_mesh==0 || other==0)
1777 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::changeUnderlyingMesh : is expected to operate on not null meshes !");
1778 DataArrayInt *cellCor=0,*nodeCor=0;
1779 other->checkGeoEquivalWith(_mesh,levOfCheck,precOnMesh,cellCor,nodeCor);
1780 MCAuto<DataArrayInt> cellCor2(cellCor),nodeCor2(nodeCor);
1782 renumberCellsWithoutMesh(cellCor->getConstPointer(),false);
1784 renumberNodesWithoutMesh(nodeCor->getConstPointer(),nodeCor->getMaxValueInArray()+1,eps);
1789 * Subtracts another field from \a this one in case when the two fields have different
1790 * supporting meshes. The subtraction is performed provided that the tho meshes can be
1791 * considered equal with use of specified equality criteria, else an exception is thrown.
1792 * If the meshes match, the mesh of \a f is set to \a this field (\a this is permuted if
1793 * necessary) and field values are subtracted. No interpolation is done here, only an
1794 * analysis of two underlying mesh is done to see if the meshes are geometrically
1796 * The job of this method consists in calling
1797 * \a this->changeUnderlyingMesh() with \a f->getMesh() as the first parameter, and then
1798 * \a this -= \a f.<br>
1799 * This method requires that \a f and \a this are coherent (checkConsistencyLight()) and that \a f
1800 * and \a this are coherent for a merge.<br>
1801 * "DM" in the method name stands for "different meshes".
1802 * \param [in] f - the field to subtract from this.
1803 * \param [in] levOfCheck - defines equality criteria used for mesh comparison. For
1804 * it's meaning explanation, see MEDCouplingMesh::checkGeoEquivalWith() which
1805 * is used for mesh comparison.
1806 * \param [in] precOnMesh - a precision used to compare nodes of the two meshes.
1807 * It is used as \a prec parameter of MEDCouplingMesh::checkGeoEquivalWith().
1808 * \param [in] eps - a precision used at node renumbering (if needed) to compare field
1809 * values at merged nodes. If the values differ more than \a eps, an
1810 * exception is thrown.
1811 * \throw If \a f == NULL.
1812 * \throw If any of the meshes is not set or is not well defined.
1813 * \throw If the two meshes do not match.
1814 * \throw If the two fields are not coherent for merge.
1815 * \throw If field values at merged nodes (if any) deffer more than \a eps.
1817 * \if ENABLE_EXAMPLES
1818 * \ref cpp_mcfielddouble_substractInPlaceDM "Here is a C++ example".<br>
1819 * \ref py_mcfielddouble_substractInPlaceDM "Here is a Python example".
1821 * \sa changeUnderlyingMesh().
1823 void MEDCouplingFieldDouble::substractInPlaceDM(const MEDCouplingFieldDouble *f, int levOfCheck, double precOnMesh, double eps)
1825 checkConsistencyLight();
1827 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::substractInPlaceDM : input field is NULL !");
1828 f->checkConsistencyLight();
1829 if(!areCompatibleForMerge(f))
1830 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::substractInPlaceDM : Fields are not compatible ; unable to apply mergeFields on them !");
1831 changeUnderlyingMesh(f->getMesh(),levOfCheck,precOnMesh,eps);
1836 * Merges coincident nodes of the underlying mesh. If some nodes are coincident, the
1837 * underlying mesh is replaced by a new mesh instance where the coincident nodes are merged.
1838 * \param [in] eps - a precision used to compare nodes of the two meshes.
1839 * \param [in] epsOnVals - a precision used to compare field
1840 * values at merged nodes. If the values differ more than \a epsOnVals, an
1841 * exception is thrown.
1842 * \return bool - \c true if some nodes have been merged and hence \a this field lies
1844 * \throw If the mesh is of type not inheriting from MEDCouplingPointSet.
1845 * \throw If the mesh is not well defined.
1846 * \throw If the spatial discretization of \a this field is NULL.
1847 * \throw If the data array is not set.
1848 * \throw If field values at merged nodes (if any) deffer more than \a epsOnVals.
1850 bool MEDCouplingFieldDouble::mergeNodes(double eps, double epsOnVals)
1852 const MEDCouplingPointSet *meshC=dynamic_cast<const MEDCouplingPointSet *>(_mesh);
1854 throw INTERP_KERNEL::Exception("Invalid support mesh to apply mergeNodes on it : must be a MEDCouplingPointSet one !");
1856 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform mergeNodes !");
1857 MCAuto<MEDCouplingPointSet> meshC2((MEDCouplingPointSet *)meshC->deepCopy());
1860 MCAuto<DataArrayInt> arr=meshC2->mergeNodes(eps,ret,ret2);
1861 if(!ret)//no nodes have been merged.
1863 std::vector<DataArrayDouble *> arrays;
1864 timeDiscr()->getArrays(arrays);
1865 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
1867 _type->renumberValuesOnNodes(epsOnVals,arr->getConstPointer(),meshC2->getNumberOfNodes(),*iter);
1873 * Merges coincident nodes of the underlying mesh. If some nodes are coincident, the
1874 * underlying mesh is replaced by a new mesh instance where the coincident nodes are
1876 * In contrast to mergeNodes(), location of merged nodes is changed to be at their barycenter.
1877 * \param [in] eps - a precision used to compare nodes of the two meshes.
1878 * \param [in] epsOnVals - a precision used to compare field
1879 * values at merged nodes. If the values differ more than \a epsOnVals, an
1880 * exception is thrown.
1881 * \return bool - \c true if some nodes have been merged and hence \a this field lies
1883 * \throw If the mesh is of type not inheriting from MEDCouplingPointSet.
1884 * \throw If the mesh is not well defined.
1885 * \throw If the spatial discretization of \a this field is NULL.
1886 * \throw If the data array is not set.
1887 * \throw If field values at merged nodes (if any) deffer more than \a epsOnVals.
1889 bool MEDCouplingFieldDouble::mergeNodesCenter(double eps, double epsOnVals)
1891 const MEDCouplingPointSet *meshC=dynamic_cast<const MEDCouplingPointSet *>(_mesh);
1893 throw INTERP_KERNEL::Exception("Invalid support mesh to apply mergeNodes on it : must be a MEDCouplingPointSet one !");
1895 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform mergeNodesCenter !");
1896 MCAuto<MEDCouplingPointSet> meshC2((MEDCouplingPointSet *)meshC->deepCopy());
1899 MCAuto<DataArrayInt> arr=meshC2->mergeNodesCenter(eps,ret,ret2);
1900 if(!ret)//no nodes have been merged.
1902 std::vector<DataArrayDouble *> arrays;
1903 timeDiscr()->getArrays(arrays);
1904 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
1906 _type->renumberValuesOnNodes(epsOnVals,arr->getConstPointer(),meshC2->getNumberOfNodes(),*iter);
1912 * Removes from the underlying mesh nodes not used in any cell. If some nodes are
1913 * removed, the underlying mesh is replaced by a new mesh instance where the unused
1914 * nodes are removed.<br>
1915 * \param [in] epsOnVals - a precision used to compare field
1916 * values at merged nodes. If the values differ more than \a epsOnVals, an
1917 * exception is thrown.
1918 * \return bool - \c true if some nodes have been removed and hence \a this field lies
1920 * \throw If the mesh is of type not inheriting from MEDCouplingPointSet.
1921 * \throw If the mesh is not well defined.
1922 * \throw If the spatial discretization of \a this field is NULL.
1923 * \throw If the data array is not set.
1924 * \throw If field values at merged nodes (if any) deffer more than \a epsOnVals.
1926 bool MEDCouplingFieldDouble::zipCoords(double epsOnVals)
1928 const MEDCouplingPointSet *meshC=dynamic_cast<const MEDCouplingPointSet *>(_mesh);
1930 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::zipCoords : Invalid support mesh to apply zipCoords on it : must be a MEDCouplingPointSet one !");
1932 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform zipCoords !");
1933 MCAuto<MEDCouplingPointSet> meshC2((MEDCouplingPointSet *)meshC->deepCopy());
1934 int oldNbOfNodes=meshC2->getNumberOfNodes();
1935 MCAuto<DataArrayInt> arr=meshC2->zipCoordsTraducer();
1936 if(meshC2->getNumberOfNodes()!=oldNbOfNodes)
1938 std::vector<DataArrayDouble *> arrays;
1939 timeDiscr()->getArrays(arrays);
1940 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
1942 _type->renumberValuesOnNodes(epsOnVals,arr->getConstPointer(),meshC2->getNumberOfNodes(),*iter);
1950 * Removes duplicates of cells from the understanding mesh. If some cells are
1951 * removed, the underlying mesh is replaced by a new mesh instance where the cells
1952 * duplicates are removed.<br>
1953 * \param [in] compType - specifies a cell comparison technique. Meaning of its
1954 * valid values [0,1,2] is explained in the description of
1955 * MEDCouplingPointSet::zipConnectivityTraducer() which is called by this method.
1956 * \param [in] epsOnVals - a precision used to compare field
1957 * values at merged cells. If the values differ more than \a epsOnVals, an
1958 * exception is thrown.
1959 * \return bool - \c true if some cells have been removed and hence \a this field lies
1961 * \throw If the mesh is not an instance of MEDCouplingUMesh.
1962 * \throw If the mesh is not well defined.
1963 * \throw If the spatial discretization of \a this field is NULL.
1964 * \throw If the data array is not set.
1965 * \throw If field values at merged cells (if any) deffer more than \a epsOnVals.
1967 bool MEDCouplingFieldDouble::zipConnectivity(int compType, double epsOnVals)
1969 const MEDCouplingUMesh *meshC=dynamic_cast<const MEDCouplingUMesh *>(_mesh);
1971 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::zipConnectivity : Invalid support mesh to apply zipCoords on it : must be a MEDCouplingPointSet one !");
1973 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform zipConnectivity !");
1974 MCAuto<MEDCouplingUMesh> meshC2((MEDCouplingUMesh *)meshC->deepCopy());
1975 int oldNbOfCells=meshC2->getNumberOfCells();
1976 MCAuto<DataArrayInt> arr=meshC2->zipConnectivityTraducer(compType);
1977 if(meshC2->getNumberOfCells()!=oldNbOfCells)
1979 std::vector<DataArrayDouble *> arrays;
1980 timeDiscr()->getArrays(arrays);
1981 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
1983 _type->renumberValuesOnCells(epsOnVals,meshC,arr->getConstPointer(),meshC2->getNumberOfCells(),*iter);
1991 * This method calls MEDCouplingUMesh::buildSlice3D method. So this method makes the assumption that underlying mesh exists.
1992 * For the moment, this method is implemented for fields on cells.
1994 * \return a newly allocated field double containing the result that the user should deallocate.
1996 MEDCouplingFieldDouble *MEDCouplingFieldDouble::extractSlice3D(const double *origin, const double *vec, double eps) const
1998 const MEDCouplingMesh *mesh=getMesh();
2000 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::extractSlice3D : underlying mesh is null !");
2001 if(getTypeOfField()!=ON_CELLS)
2002 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::extractSlice3D : only implemented for fields on cells !");
2003 const MCAuto<MEDCouplingUMesh> umesh(mesh->buildUnstructured());
2004 MCAuto<MEDCouplingFieldDouble> ret(clone(false));
2005 ret->setMesh(umesh);
2006 DataArrayInt *cellIds=0;
2007 MCAuto<MEDCouplingUMesh> mesh2=umesh->buildSlice3D(origin,vec,eps,cellIds);
2008 MCAuto<DataArrayInt> cellIds2=cellIds;
2009 ret->setMesh(mesh2);
2010 MCAuto<DataArrayInt> tupleIds=computeTupleIdsToSelectFromCellIds(cellIds->begin(),cellIds->end());
2011 std::vector<DataArrayDouble *> arrays;
2012 timeDiscr()->getArrays(arrays);
2014 std::vector<DataArrayDouble *> newArr(arrays.size());
2015 std::vector< MCAuto<DataArrayDouble> > newArr2(arrays.size());
2016 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++,i++)
2020 newArr2[i]=(*iter)->selectByTupleIdSafe(cellIds->begin(),cellIds->end());
2021 newArr[i]=newArr2[i];
2024 ret->setArrays(newArr);
2029 * Divides every cell of the underlying mesh into simplices (triangles in 2D and
2030 * tetrahedra in 3D). If some cells are divided, the underlying mesh is replaced by a new
2031 * mesh instance containing the simplices.<br>
2032 * \param [in] policy - specifies a pattern used for splitting. For its description, see
2033 * MEDCouplingUMesh::simplexize().
2034 * \return bool - \c true if some cells have been divided and hence \a this field lies
2036 * \throw If \a policy has an invalid value. For valid values, see the description of
2037 * MEDCouplingUMesh::simplexize().
2038 * \throw If MEDCouplingMesh::simplexize() is not applicable to the underlying mesh.
2039 * \throw If the mesh is not well defined.
2040 * \throw If the spatial discretization of \a this field is NULL.
2041 * \throw If the data array is not set.
2043 bool MEDCouplingFieldDouble::simplexize(int policy)
2046 throw INTERP_KERNEL::Exception("No underlying mesh on this field to perform simplexize !");
2048 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform simplexize !");
2049 int oldNbOfCells=_mesh->getNumberOfCells();
2050 MCAuto<MEDCouplingMesh> meshC2(_mesh->deepCopy());
2051 MCAuto<DataArrayInt> arr=meshC2->simplexize(policy);
2052 int newNbOfCells=meshC2->getNumberOfCells();
2053 if(oldNbOfCells==newNbOfCells)
2055 std::vector<DataArrayDouble *> arrays;
2056 timeDiscr()->getArrays(arrays);
2057 for(std::vector<DataArrayDouble *>::const_iterator iter=arrays.begin();iter!=arrays.end();iter++)
2059 _type->renumberValuesOnCellsR(_mesh,arr->getConstPointer(),arr->getNbOfElems(),*iter);
2065 * This method makes the hypothesis that \a this is a Gauss field. This method returns a newly created field on cells with same number of tuples than \a this.
2066 * Each Gauss points in \a this is replaced by a polygon or polyhedron cell with associated region following Voronoi algorithm.
2068 MCAuto<MEDCouplingFieldDouble> MEDCouplingFieldDouble::voronoize(double eps) const
2070 checkConsistencyLight();
2071 const MEDCouplingMesh *mesh(getMesh());
2072 INTERP_KERNEL::AutoCppPtr<Voronizer> vor;
2073 int meshDim(mesh->getMeshDimension()),spaceDim(mesh->getSpaceDimension());
2074 if(meshDim==1 && (spaceDim==1 || spaceDim==2 || spaceDim==3))
2075 vor=new Voronizer1D;
2076 else if(meshDim==2 && (spaceDim==2 || spaceDim==3))
2077 vor=new Voronizer2D;
2078 else if(meshDim==3 && spaceDim==3)
2079 vor=new Voronizer3D;
2081 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::voronoize : only 2D, 3D surf, and 3D are supported for the moment !");
2082 return voronoizeGen(vor,eps);
2086 * \sa MEDCouplingUMesh::convertQuadraticCellsToLinear
2088 MCAuto<MEDCouplingFieldDouble> MEDCouplingFieldDouble::convertQuadraticCellsToLinear() const
2090 checkConsistencyLight();
2091 switch(getTypeOfField())
2095 const MEDCouplingMesh *mesh(getMesh());
2097 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::convertQuadraticCellsToLinear : null mesh !");
2098 MCAuto<MEDCouplingUMesh> umesh(mesh->buildUnstructured());
2099 umesh=umesh->clone(false);
2100 umesh->convertQuadraticCellsToLinear();
2101 MCAuto<DataArrayInt> o2n(umesh->zipCoordsTraducer());
2102 MCAuto<DataArrayInt> n2o(o2n->invertArrayO2N2N2O(umesh->getNumberOfNodes()));
2103 MCAuto<DataArrayDouble> arr(getArray()->selectByTupleIdSafe(n2o->begin(),n2o->end()));
2104 MCAuto<MEDCouplingFieldDouble> ret(MEDCouplingFieldDouble::New(ON_NODES));
2106 ret->setMesh(umesh);
2107 ret->copyAllTinyAttrFrom(this);
2112 const MEDCouplingMesh *mesh(getMesh());
2114 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::convertQuadraticCellsToLinear : null mesh !");
2115 MCAuto<MEDCouplingUMesh> umesh(mesh->buildUnstructured());
2116 umesh=umesh->clone(false);
2117 umesh->convertQuadraticCellsToLinear();
2119 MCAuto<MEDCouplingFieldDouble> ret(MEDCouplingFieldDouble::New(ON_CELLS));
2120 ret->setArray(const_cast<DataArrayDouble *>(getArray()));
2121 ret->setMesh(umesh);
2122 ret->copyAllTinyAttrFrom(this);
2127 const MEDCouplingMesh *mesh(getMesh());
2129 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::convertQuadraticCellsToLinear : null mesh !");
2130 MCAuto<MEDCouplingUMesh> umesh(mesh->buildUnstructured());
2131 std::set<INTERP_KERNEL::NormalizedCellType> gt(umesh->getAllGeoTypes());
2132 MCAuto<MEDCouplingFieldDouble> ret(MEDCouplingFieldDouble::New(ON_GAUSS_PT));
2134 const MEDCouplingFieldDiscretization *disc(getDiscretization());
2135 const MEDCouplingFieldDiscretizationGauss *disc2(dynamic_cast<const MEDCouplingFieldDiscretizationGauss *>(disc));
2137 throw INTERP_KERNEL::Exception("convertQuadraticCellsToLinear : Not a ON_GAUSS_PT field");
2138 std::set<INTERP_KERNEL::NormalizedCellType> gt2(umesh->getAllGeoTypes());
2139 const DataArrayDouble *arr(getArray());
2140 std::vector< MCAuto<DataArrayInt> > cellIdsV;
2141 std::vector< MCAuto<MEDCouplingUMesh> > meshesV;
2142 std::vector< MEDCouplingGaussLocalization > glV;
2143 bool isZipReq(false);
2144 for(std::set<INTERP_KERNEL::NormalizedCellType>::const_iterator it=gt.begin();it!=gt.end();it++)
2146 const INTERP_KERNEL::CellModel& cm(INTERP_KERNEL::CellModel::GetCellModel(*it));
2147 MCAuto<DataArrayInt> cellIds(umesh->giveCellsWithType(*it));
2148 cellIdsV.push_back(cellIds);
2149 MCAuto<MEDCouplingUMesh> part(umesh->buildPartOfMySelf(cellIds->begin(),cellIds->end()));
2150 int id(disc2->getGaussLocalizationIdOfOneType(*it));
2151 const MEDCouplingGaussLocalization& gl(disc2->getGaussLocalization(id));
2152 if(!cm.isQuadratic())
2159 part->convertQuadraticCellsToLinear();
2160 INTERP_KERNEL::GaussInfo gi(*it,gl.getGaussCoords(),gl.getNumberOfGaussPt(),gl.getRefCoords(),gl.getNumberOfPtsInRefCell());
2161 INTERP_KERNEL::GaussInfo gi2(gi.convertToLinear());
2162 MEDCouplingGaussLocalization gl2(gi2.getGeoType(),gi2.getRefCoords(),gi2.getGaussCoords(),gl.getWeights());
2165 meshesV.push_back(part);
2169 std::vector< const MEDCouplingUMesh * > meshesPtr(VecAutoToVecOfCstPt(meshesV));
2170 umesh=MEDCouplingUMesh::MergeUMeshesOnSameCoords(meshesPtr);
2171 std::vector< const DataArrayInt * > zeCellIds(VecAutoToVecOfCstPt(cellIdsV));
2172 MCAuto<DataArrayInt> zeIds(DataArrayInt::Aggregate(zeCellIds));
2173 umesh->renumberCells(zeIds->begin());
2174 umesh->setName(mesh->getName());
2179 ret->setArray(const_cast<DataArrayDouble *>(getArray()));
2180 ret->setMesh(umesh);
2181 for(std::vector< MEDCouplingGaussLocalization >::const_iterator it=glV.begin();it!=glV.end();it++)
2182 ret->setGaussLocalizationOnType((*it).getType(),(*it).getRefCoords(),(*it).getGaussCoords(),(*it).getWeights());
2183 ret->copyAllTinyAttrFrom(this);
2184 ret->checkConsistencyLight();
2188 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::convertQuadraticCellsToLinear : Only available for fields on nodes and on cells !");
2193 * This is expected to be a 3 components vector field on nodes (if not an exception will be thrown). \a this is also expected to lie on a MEDCouplingPointSet mesh.
2194 * Finaly \a this is also expected to be consistent.
2195 * In these conditions this method returns a newly created field (to be dealed by the caller).
2196 * The returned field will also 3 compo vector field be on nodes lying on the same mesh than \a this.
2198 * For each 3 compo tuple \a tup in \a this the returned tuple is the result of the transformation of \a tup in the new referential. This referential is defined by \a Ur, \a Uteta, \a Uz.
2199 * \a Ur is the vector between \a center point and the associated node with \a tuple. \a Uz is \a vect normalized. And Uteta is the cross product of \a Uz with \a Ur.
2201 * \sa DataArrayDouble::fromCartToCylGiven
2203 MEDCouplingFieldDouble *MEDCouplingFieldDouble::computeVectorFieldCyl(const double center[3], const double vect[3]) const
2205 checkConsistencyLight();
2206 const DataArrayDouble *coo(getMesh()->getDirectAccessOfCoordsArrIfInStructure());
2207 MEDCouplingTimeDiscretization *td(timeDiscr()->computeVectorFieldCyl(coo,center,vect));
2208 td->copyTinyAttrFrom(*timeDiscr());
2209 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2210 ret->setMesh(getMesh());
2211 ret->setName(getName());
2216 * Creates a new MEDCouplingFieldDouble filled with the doubly contracted product of
2217 * every tensor of \a this 6-componental field.
2218 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble, whose
2219 * each tuple is calculated from the tuple <em>(t)</em> of \a this field as
2220 * follows: \f$ t[0]^2+t[1]^2+t[2]^2+2*t[3]^2+2*t[4]^2+2*t[5]^2\f$.
2221 * This new field lies on the same mesh as \a this one. The caller is to delete
2222 * this field using decrRef() as it is no more needed.
2223 * \throw If \a this->getNumberOfComponents() != 6.
2224 * \throw If the spatial discretization of \a this field is NULL.
2226 MEDCouplingFieldDouble *MEDCouplingFieldDouble::doublyContractedProduct() const
2229 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform doublyContractedProduct !");
2230 MEDCouplingTimeDiscretization *td(timeDiscr()->doublyContractedProduct());
2231 td->copyTinyAttrFrom(*timeDiscr());
2232 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2233 ret->setName("DoublyContractedProduct");
2234 ret->setMesh(getMesh());
2239 * Creates a new MEDCouplingFieldDouble filled with the determinant of a square
2240 * matrix defined by every tuple of \a this field, having either 4, 6 or 9 components.
2241 * The case of 6 components corresponds to that of the upper triangular matrix.
2242 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble, whose
2243 * each tuple is the determinant of matrix of the corresponding tuple of \a this
2244 * field. This new field lies on the same mesh as \a this one. The caller is to
2245 * delete this field using decrRef() as it is no more needed.
2246 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2247 * \throw If the spatial discretization of \a this field is NULL.
2249 MEDCouplingFieldDouble *MEDCouplingFieldDouble::determinant() const
2252 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform determinant !");
2253 MEDCouplingTimeDiscretization *td(timeDiscr()->determinant());
2254 td->copyTinyAttrFrom(*timeDiscr());
2255 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2256 ret->setName("Determinant");
2257 ret->setMesh(getMesh());
2263 * Creates a new MEDCouplingFieldDouble with 3 components filled with 3 eigenvalues of
2264 * an upper triangular matrix defined by every tuple of \a this 6-componental field.
2265 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble,
2266 * having 3 components, whose each tuple contains the eigenvalues of the matrix of
2267 * corresponding tuple of \a this field. This new field lies on the same mesh as
2268 * \a this one. The caller is to delete this field using decrRef() as it is no
2270 * \throw If \a this->getNumberOfComponents() != 6.
2271 * \throw If the spatial discretization of \a this field is NULL.
2273 MEDCouplingFieldDouble *MEDCouplingFieldDouble::eigenValues() const
2276 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform eigenValues !");
2277 MEDCouplingTimeDiscretization *td(timeDiscr()->eigenValues());
2278 td->copyTinyAttrFrom(*timeDiscr());
2279 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2280 ret->setName("EigenValues");
2281 ret->setMesh(getMesh());
2286 * Creates a new MEDCouplingFieldDouble with 9 components filled with 3 eigenvectors of
2287 * an upper triangular matrix defined by every tuple of \a this 6-componental field.
2288 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble,
2289 * having 9 components, whose each tuple contains the eigenvectors of the matrix of
2290 * corresponding tuple of \a this field. This new field lies on the same mesh as
2291 * \a this one. The caller is to delete this field using decrRef() as it is no
2293 * \throw If \a this->getNumberOfComponents() != 6.
2294 * \throw If the spatial discretization of \a this field is NULL.
2296 MEDCouplingFieldDouble *MEDCouplingFieldDouble::eigenVectors() const
2299 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform eigenVectors !");
2300 MEDCouplingTimeDiscretization *td(timeDiscr()->eigenVectors());
2301 td->copyTinyAttrFrom(*timeDiscr());
2302 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2303 ret->setName("EigenVectors");
2304 ret->setMesh(getMesh());
2309 * Creates a new MEDCouplingFieldDouble filled with the inverse matrix of
2310 * a matrix defined by every tuple of \a this field having either 4, 6 or 9
2311 * components. The case of 6 components corresponds to that of the upper triangular
2313 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble,
2314 * having the same number of components as \a this one, whose each tuple
2315 * contains the inverse matrix of the matrix of corresponding tuple of \a this
2316 * field. This new field lies on the same mesh as \a this one. The caller is to
2317 * delete this field using decrRef() as it is no more needed.
2318 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2319 * \throw If the spatial discretization of \a this field is NULL.
2321 MEDCouplingFieldDouble *MEDCouplingFieldDouble::inverse() const
2324 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform inverse !");
2325 MEDCouplingTimeDiscretization *td(timeDiscr()->inverse());
2326 td->copyTinyAttrFrom(*timeDiscr());
2327 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2328 ret->setName("Inversion");
2329 ret->setMesh(getMesh());
2334 * Creates a new MEDCouplingFieldDouble filled with the trace of
2335 * a matrix defined by every tuple of \a this field having either 4, 6 or 9
2336 * components. The case of 6 components corresponds to that of the upper triangular
2338 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble,
2339 * having 1 component, whose each tuple is the trace of the matrix of
2340 * corresponding tuple of \a this field.
2341 * This new field lies on the same mesh as \a this one. The caller is to
2342 * delete this field using decrRef() as it is no more needed.
2343 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2344 * \throw If the spatial discretization of \a this field is NULL.
2346 MEDCouplingFieldDouble *MEDCouplingFieldDouble::trace() const
2349 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform trace !");
2350 MEDCouplingTimeDiscretization *td(timeDiscr()->trace());
2351 td->copyTinyAttrFrom(*timeDiscr());
2352 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2353 ret->setName("Trace");
2354 ret->setMesh(getMesh());
2359 * Creates a new MEDCouplingFieldDouble filled with the stress deviator tensor of
2360 * a stress tensor defined by every tuple of \a this 6-componental field.
2361 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble,
2362 * having same number of components and tuples as \a this field,
2363 * whose each tuple contains the stress deviator tensor of the stress tensor of
2364 * corresponding tuple of \a this field. This new field lies on the same mesh as
2365 * \a this one. The caller is to delete this field using decrRef() as it is no
2367 * \throw If \a this->getNumberOfComponents() != 6.
2368 * \throw If the spatial discretization of \a this field is NULL.
2370 MEDCouplingFieldDouble *MEDCouplingFieldDouble::deviator() const
2373 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform deviator !");
2374 MEDCouplingTimeDiscretization *td(timeDiscr()->deviator());
2375 td->copyTinyAttrFrom(*timeDiscr());
2376 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2377 ret->setName("Deviator");
2378 ret->setMesh(getMesh());
2383 * Creates a new MEDCouplingFieldDouble filled with the magnitude of
2384 * every vector of \a this field.
2385 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble,
2386 * having one component, whose each tuple is the magnitude of the vector
2387 * of corresponding tuple of \a this field. This new field lies on the
2388 * same mesh as \a this one. The caller is to
2389 * delete this field using decrRef() as it is no more needed.
2390 * \throw If the spatial discretization of \a this field is NULL.
2392 MEDCouplingFieldDouble *MEDCouplingFieldDouble::magnitude() const
2395 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform magnitude !");
2396 MEDCouplingTimeDiscretization *td(timeDiscr()->magnitude());
2397 td->copyTinyAttrFrom(*timeDiscr());
2398 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2399 ret->setName("Magnitude");
2400 ret->setMesh(getMesh());
2405 * Creates a new scalar MEDCouplingFieldDouble filled with the maximal value among
2406 * values of every tuple of \a this field.
2407 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2408 * This new field lies on the same mesh as \a this one. The caller is to
2409 * delete this field using decrRef() as it is no more needed.
2410 * \throw If the spatial discretization of \a this field is NULL.
2412 MEDCouplingFieldDouble *MEDCouplingFieldDouble::maxPerTuple() const
2415 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform maxPerTuple !");
2416 MEDCouplingTimeDiscretization *td(timeDiscr()->maxPerTuple());
2417 td->copyTinyAttrFrom(*timeDiscr());
2418 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2419 std::ostringstream oss;
2420 oss << "Max_" << getName();
2421 ret->setName(oss.str());
2422 ret->setMesh(getMesh());
2427 * Changes number of components in \a this field. If \a newNbOfComp is less
2428 * than \a this->getNumberOfComponents() then each tuple
2429 * is truncated to have \a newNbOfComp components, keeping first components. If \a
2430 * newNbOfComp is more than \a this->getNumberOfComponents() then
2431 * each tuple is populated with \a dftValue to have \a newNbOfComp components.
2432 * \param [in] newNbOfComp - number of components for the new field to have.
2433 * \param [in] dftValue - value assigned to new values added to \a this field.
2434 * \throw If \a this is not allocated.
2436 void MEDCouplingFieldDouble::changeNbOfComponents(int newNbOfComp, double dftValue)
2438 timeDiscr()->changeNbOfComponents(newNbOfComp,dftValue);
2442 * Creates a new MEDCouplingFieldDouble composed of selected components of \a this field.
2443 * The new MEDCouplingFieldDouble has the same number of tuples but includes components
2444 * specified by \a compoIds parameter. So that getNbOfElems() of the result field
2445 * can be either less, same or more than \a this->getNumberOfValues().
2446 * \param [in] compoIds - sequence of zero based indices of components to include
2447 * into the new field.
2448 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble that the caller
2449 * is to delete using decrRef() as it is no more needed.
2450 * \throw If a component index (\a i) is not valid:
2451 * \a i < 0 || \a i >= \a this->getNumberOfComponents().
2453 MEDCouplingFieldDouble *MEDCouplingFieldDouble::keepSelectedComponents(const std::vector<int>& compoIds) const
2456 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform keepSelectedComponents !");
2457 MEDCouplingTimeDiscretization *td(timeDiscr()->keepSelectedComponents(compoIds));
2458 td->copyTinyAttrFrom(*timeDiscr());
2459 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2460 ret->setName(getName());
2461 ret->setMesh(getMesh());
2467 * Copy all components in a specified order from another field.
2468 * The number of tuples in \a this and the other field can be different.
2469 * \param [in] f - the field to copy data from.
2470 * \param [in] compoIds - sequence of zero based indices of components, data of which is
2472 * \throw If the two fields have different number of data arrays.
2473 * \throw If a data array is set in one of fields and is not set in the other.
2474 * \throw If \a compoIds.size() != \a a->getNumberOfComponents().
2475 * \throw If \a compoIds[i] < 0 or \a compoIds[i] > \a this->getNumberOfComponents().
2477 void MEDCouplingFieldDouble::setSelectedComponents(const MEDCouplingFieldDouble *f, const std::vector<int>& compoIds)
2479 timeDiscr()->setSelectedComponents(f->timeDiscr(),compoIds);
2483 * Sorts value within every tuple of \a this field.
2484 * \param [in] asc - if \a true, the values are sorted in ascending order, else,
2485 * in descending order.
2486 * \throw If a data array is not allocated.
2488 void MEDCouplingFieldDouble::sortPerTuple(bool asc)
2490 timeDiscr()->sortPerTuple(asc);
2494 * Creates a new MEDCouplingFieldDouble by concatenating two given fields.
2496 * the first field precede values of the second field within the result field.
2497 * \param [in] f1 - the first field.
2498 * \param [in] f2 - the second field.
2499 * \return MEDCouplingFieldDouble * - the result field. It is a new instance of
2500 * MEDCouplingFieldDouble. The caller is to delete this mesh using decrRef()
2501 * as it is no more needed.
2502 * \throw If the fields are not compatible for the merge.
2503 * \throw If the spatial discretization of \a f1 is NULL.
2504 * \throw If the time discretization of \a f1 is NULL.
2506 * \if ENABLE_EXAMPLES
2507 * \ref cpp_mcfielddouble_MergeFields "Here is a C++ example".<br>
2508 * \ref py_mcfielddouble_MergeFields "Here is a Python example".
2511 MEDCouplingFieldDouble *MEDCouplingFieldDouble::MergeFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2513 if(!f1->areCompatibleForMerge(f2))
2514 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply MergeFields on them ! Check support mesh, field nature, and spatial and time discretisation.");
2515 const MEDCouplingMesh *m1(f1->getMesh()),*m2(f2->getMesh());
2516 if(!f1->timeDiscr())
2517 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::MergeFields : no time discr of f1 !");
2519 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::MergeFields : no spatial discr of f1 !");
2520 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->aggregate(f2->timeDiscr()));
2521 td->copyTinyAttrFrom(*f1->timeDiscr());
2522 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(f1->getNature(),td,f1->_type->clone()));
2523 ret->setName(f1->getName());
2524 ret->setDescription(f1->getDescription());
2527 MCAuto<MEDCouplingMesh> m=m1->mergeMyselfWith(m2);
2534 * Creates a new MEDCouplingFieldDouble by concatenating all given fields.
2535 * Values of the *i*-th field precede values of the (*i*+1)-th field within the result.
2536 * If there is only one field in \a a, a deepCopy() (except time information of mesh and
2537 * field) of the field is returned.
2538 * Generally speaking the first field in \a a is used to assign tiny attributes of the
2540 * \param [in] a - a vector of fields (MEDCouplingFieldDouble) to concatenate.
2541 * \return MEDCouplingFieldDouble * - the result field. It is a new instance of
2542 * MEDCouplingFieldDouble. The caller is to delete this mesh using decrRef()
2543 * as it is no more needed.
2544 * \throw If \a a is empty.
2545 * \throw If the fields are not compatible for the merge.
2547 * \if ENABLE_EXAMPLES
2548 * \ref cpp_mcfielddouble_MergeFields "Here is a C++ example".<br>
2549 * \ref py_mcfielddouble_MergeFields "Here is a Python example".
2552 MEDCouplingFieldDouble *MEDCouplingFieldDouble::MergeFields(const std::vector<const MEDCouplingFieldDouble *>& a)
2555 throw INTERP_KERNEL::Exception("FieldDouble::MergeFields : size of array must be >= 1 !");
2556 std::vector< MCAuto<MEDCouplingUMesh> > ms(a.size());
2557 std::vector< const MEDCouplingUMesh *> ms2(a.size());
2558 std::vector< const MEDCouplingTimeDiscretization *> tds(a.size());
2559 std::vector<const MEDCouplingFieldDouble *>::const_iterator it=a.begin();
2560 const MEDCouplingFieldDouble *ref=(*it++);
2562 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::MergeFields : presence of NULL instance in first place of input vector !");
2563 for(;it!=a.end();it++)
2564 if(!ref->areCompatibleForMerge(*it))
2565 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply MergeFields on them! Check support mesh, field nature, and spatial and time discretisation.");
2566 for(int i=0;i<(int)a.size();i++)
2569 { ms[i]=a[i]->getMesh()->buildUnstructured(); ms2[i]=ms[i]; }
2571 { ms[i]=0; ms2[i]=0; }
2572 tds[i]=a[i]->timeDiscr();
2574 MEDCouplingTimeDiscretization *td(tds[0]->aggregate(tds));
2575 td->copyTinyAttrFrom(*(a[0]->timeDiscr()));
2576 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(a[0]->getNature(),td,a[0]->_type->clone()));
2577 ret->setName(a[0]->getName());
2578 ret->setDescription(a[0]->getDescription());
2581 MCAuto<MEDCouplingUMesh> m(MEDCouplingUMesh::MergeUMeshes(ms2));
2582 m->copyTinyInfoFrom(ms2[0]);
2589 * Creates a new MEDCouplingFieldDouble by concatenating components of two given fields.
2590 * The number of components in the result field is a sum of the number of components of
2591 * given fields. The number of tuples in the result field is same as that of each of given
2593 * Number of tuples in the given fields must be the same.
2594 * \param [in] f1 - a field to include in the result field.
2595 * \param [in] f2 - another field to include in the result field.
2596 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2597 * The caller is to delete this result field using decrRef() as it is no more
2599 * \throw If the fields are not compatible for a meld (areCompatibleForMeld()).
2600 * \throw If any of data arrays is not allocated.
2601 * \throw If \a f1->getNumberOfTuples() != \a f2->getNumberOfTuples()
2603 MEDCouplingFieldDouble *MEDCouplingFieldDouble::MeldFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2606 throw INTERP_KERNEL::Exception("MeldFields : null input pointer !");
2607 if(!f1->areCompatibleForMeld(f2))
2608 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply MeldFields on them ! Check support mesh, field nature, and spatial and time discretisation.");
2609 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->meld(f2->timeDiscr()));
2610 td->copyTinyAttrFrom(*f1->timeDiscr());
2611 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(f1->getNature(),td,f1->_type->clone()));
2612 ret->setMesh(f1->getMesh());
2617 * Returns a new MEDCouplingFieldDouble containing a dot product of two given fields,
2618 * so that the i-th tuple of the result field is a sum of products of j-th components of
2619 * i-th tuples of given fields (\f$ f_i = \sum_{j=1}^n f1_j * f2_j \f$).
2620 * Number of tuples and components in the given fields must be the same.
2621 * \param [in] f1 - a given field.
2622 * \param [in] f2 - another given field.
2623 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2624 * The caller is to delete this result field using decrRef() as it is no more
2626 * \throw If either \a f1 or \a f2 is NULL.
2627 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2628 * differ not only in values.
2630 MEDCouplingFieldDouble *MEDCouplingFieldDouble::DotFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2633 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::DotFields : input field is NULL !");
2634 if(!f1->areStrictlyCompatibleForMulDiv(f2))
2635 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply DotFields on them! Check support mesh, and spatial and time discretisation.");
2636 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->dot(f2->timeDiscr()));
2637 td->copyTinyAttrFrom(*f1->timeDiscr());
2638 MEDCouplingFieldDouble *ret(new MEDCouplingFieldDouble(NoNature,td,f1->_type->clone()));
2639 ret->setMesh(f1->getMesh());
2644 * Returns a new MEDCouplingFieldDouble containing a cross product of two given fields,
2646 * the i-th tuple of the result field is a 3D vector which is a cross
2647 * product of two vectors defined by the i-th tuples of given fields.
2648 * Number of tuples in the given fields must be the same.
2649 * Number of components in the given fields must be 3.
2650 * \param [in] f1 - a given field.
2651 * \param [in] f2 - another given field.
2652 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2653 * The caller is to delete this result field using decrRef() as it is no more
2655 * \throw If either \a f1 or \a f2 is NULL.
2656 * \throw If \a f1->getNumberOfComponents() != 3
2657 * \throw If \a f2->getNumberOfComponents() != 3
2658 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2659 * differ not only in values.
2661 MEDCouplingFieldDouble *MEDCouplingFieldDouble::CrossProductFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2664 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::CrossProductFields : input field is NULL !");
2665 if(!f1->areStrictlyCompatibleForMulDiv(f2))
2666 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply CrossProductFields on them! Check support mesh, and spatial and time discretisation.");
2667 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->crossProduct(f2->timeDiscr()));
2668 td->copyTinyAttrFrom(*f1->timeDiscr());
2669 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(NoNature,td,f1->_type->clone()));
2670 ret->setMesh(f1->getMesh());
2675 * Returns a new MEDCouplingFieldDouble containing maximal values of two given fields.
2676 * Number of tuples and components in the given fields must be the same.
2677 * \param [in] f1 - a field to compare values with another one.
2678 * \param [in] f2 - another field to compare values with the first one.
2679 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2680 * The caller is to delete this result field using decrRef() as it is no more
2682 * \throw If either \a f1 or \a f2 is NULL.
2683 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2684 * differ not only in values.
2686 * \if ENABLE_EXAMPLES
2687 * \ref cpp_mcfielddouble_MaxFields "Here is a C++ example".<br>
2688 * \ref py_mcfielddouble_MaxFields "Here is a Python example".
2691 MEDCouplingFieldDouble *MEDCouplingFieldDouble::MaxFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2694 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::MaxFields : input field is NULL !");
2695 if(!f1->areStrictlyCompatible(f2))
2696 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply MaxFields on them! Check support mesh, field nature, and spatial and time discretisation.");
2697 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->max(f2->timeDiscr()));
2698 td->copyTinyAttrFrom(*f1->timeDiscr());
2699 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(f1->getNature(),td,f1->_type->clone()));
2700 ret->setMesh(f1->getMesh());
2705 * Returns a new MEDCouplingFieldDouble containing minimal values of two given fields.
2706 * Number of tuples and components in the given fields must be the same.
2707 * \param [in] f1 - a field to compare values with another one.
2708 * \param [in] f2 - another field to compare values with the first one.
2709 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2710 * The caller is to delete this result field using decrRef() as it is no more
2712 * \throw If either \a f1 or \a f2 is NULL.
2713 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2714 * differ not only in values.
2716 * \if ENABLE_EXAMPLES
2717 * \ref cpp_mcfielddouble_MaxFields "Here is a C++ example".<br>
2718 * \ref py_mcfielddouble_MaxFields "Here is a Python example".
2721 MEDCouplingFieldDouble *MEDCouplingFieldDouble::MinFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2724 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::MinFields : input field is NULL !");
2725 if(!f1->areStrictlyCompatible(f2))
2726 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply MinFields on them! Check support mesh, field nature, and spatial and time discretisation.");
2727 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->min(f2->timeDiscr()));
2728 td->copyTinyAttrFrom(*f1->timeDiscr());
2729 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(f1->getNature(),td,f1->_type->clone()));
2730 ret->setMesh(f1->getMesh());
2735 * Returns a copy of \a this field in which sign of all values is reversed.
2736 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble
2737 * containing the same number of tuples and components as \a this field.
2738 * The caller is to delete this result field using decrRef() as it is no more
2740 * \throw If the spatial discretization of \a this field is NULL.
2741 * \throw If a data array is not allocated.
2743 MEDCouplingFieldDouble *MEDCouplingFieldDouble::negate() const
2746 throw INTERP_KERNEL::Exception("No spatial discretization underlying this field to perform negate !");
2747 MEDCouplingTimeDiscretization *td(timeDiscr()->negate());
2748 td->copyTinyAttrFrom(*timeDiscr());
2749 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(getNature(),td,_type->clone()));
2750 ret->setMesh(getMesh());
2755 * Returns a new MEDCouplingFieldDouble containing sum values of corresponding values of
2756 * two given fields ( _f_ [ i, j ] = _f1_ [ i, j ] + _f2_ [ i, j ] ).
2757 * Number of tuples and components in the given fields must be the same.
2758 * \param [in] f1 - a field to sum up.
2759 * \param [in] f2 - another field to sum up.
2760 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2761 * The caller is to delete this result field using decrRef() as it is no more
2763 * \throw If either \a f1 or \a f2 is NULL.
2764 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2765 * differ not only in values.
2767 MEDCouplingFieldDouble *MEDCouplingFieldDouble::AddFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2770 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::AddFields : input field is NULL !");
2771 if(!f1->areStrictlyCompatible(f2))
2772 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply AddFields on them! Check support mesh, field nature, and spatial and time discretisation.");
2773 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->add(f2->timeDiscr()));
2774 td->copyTinyAttrFrom(*f1->timeDiscr());
2775 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(f1->getNature(),td,f1->_type->clone()));
2776 ret->setMesh(f1->getMesh());
2781 * Adds values of another MEDCouplingFieldDouble to values of \a this one
2782 * ( _this_ [ i, j ] += _other_ [ i, j ] ) using DataArrayDouble::addEqual().
2783 * The two fields must have same number of tuples, components and same underlying mesh.
2784 * \param [in] other - the field to add to \a this one.
2785 * \return const MEDCouplingFieldDouble & - a reference to \a this field.
2786 * \throw If \a other is NULL.
2787 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2788 * differ not only in values.
2790 const MEDCouplingFieldDouble &MEDCouplingFieldDouble::operator+=(const MEDCouplingFieldDouble& other)
2792 if(!areStrictlyCompatible(&other))
2793 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply += on them! Check support mesh, field nature, and spatial and time discretisation.");
2794 timeDiscr()->addEqual(other.timeDiscr());
2799 * Returns a new MEDCouplingFieldDouble containing subtraction of corresponding values of
2800 * two given fields ( _f_ [ i, j ] = _f1_ [ i, j ] - _f2_ [ i, j ] ).
2801 * Number of tuples and components in the given fields must be the same.
2802 * \param [in] f1 - a field to subtract from.
2803 * \param [in] f2 - a field to subtract.
2804 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble.
2805 * The caller is to delete this result field using decrRef() as it is no more
2807 * \throw If either \a f1 or \a f2 is NULL.
2808 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2809 * differ not only in values.
2811 MEDCouplingFieldDouble *MEDCouplingFieldDouble::SubstractFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2814 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::SubstractFields : input field is NULL !");
2815 if(!f1->areStrictlyCompatible(f2))
2816 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply SubstractFields on them! Check support mesh, field nature, and spatial and time discretisation.");
2817 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->substract(f2->timeDiscr()));
2818 td->copyTinyAttrFrom(*f1->timeDiscr());
2819 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(f1->getNature(),td,f1->_type->clone()));
2820 ret->setMesh(f1->getMesh());
2825 * Subtract values of another MEDCouplingFieldDouble from values of \a this one
2826 * ( _this_ [ i, j ] -= _other_ [ i, j ] ) using DataArrayDouble::substractEqual().
2827 * The two fields must have same number of tuples, components and same underlying mesh.
2828 * \param [in] other - the field to subtract from \a this one.
2829 * \return const MEDCouplingFieldDouble & - a reference to \a this field.
2830 * \throw If \a other is NULL.
2831 * \throw If the fields are not strictly compatible (areStrictlyCompatible()), i.e. they
2832 * differ not only in values.
2834 const MEDCouplingFieldDouble &MEDCouplingFieldDouble::operator-=(const MEDCouplingFieldDouble& other)
2836 if(!areStrictlyCompatible(&other))
2837 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply -= on them! Check support mesh, field nature, and spatial and time discretisation.");
2838 timeDiscr()->substractEqual(other.timeDiscr());
2843 * Returns a new MEDCouplingFieldDouble containing product values of
2844 * two given fields. There are 2 valid cases.
2845 * 1. The fields have same number of tuples and components. Then each value of
2846 * the result field (_f_) is a product of the corresponding values of _f1_ and
2847 * _f2_, i.e. _f_ [ i, j ] = _f1_ [ i, j ] * _f2_ [ i, j ].
2848 * 2. The fields have same number of tuples and one field, say _f2_, has one
2850 * _f_ [ i, j ] = _f1_ [ i, j ] * _f2_ [ i, 0 ].
2852 * The two fields must have same number of tuples and same underlying mesh.
2853 * \param [in] f1 - a factor field.
2854 * \param [in] f2 - another factor field.
2855 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble, with no nature set.
2856 * The caller is to delete this result field using decrRef() as it is no more
2858 * \throw If either \a f1 or \a f2 is NULL.
2859 * \throw If the fields are not compatible for multiplication (areCompatibleForMul()),
2860 * i.e. they differ not only in values and possibly number of components.
2862 MEDCouplingFieldDouble *MEDCouplingFieldDouble::MultiplyFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2865 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::MultiplyFields : input field is NULL !");
2866 if(!f1->areCompatibleForMul(f2))
2867 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply MultiplyFields on them! Check support mesh, and spatial and time discretisation.");
2868 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->multiply(f2->timeDiscr()));
2869 td->copyTinyAttrFrom(*f1->timeDiscr());
2870 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(NoNature,td,f1->_type->clone()));
2871 ret->setMesh(f1->getMesh());
2876 * Multiply values of another MEDCouplingFieldDouble to values of \a this one
2877 * using DataArrayDouble::multiplyEqual().
2878 * The two fields must have same number of tuples and same underlying mesh.
2879 * There are 2 valid cases.
2880 * 1. The fields have same number of components. Then each value of
2881 * \a other is multiplied to the corresponding value of \a this field, i.e.
2882 * _this_ [ i, j ] *= _other_ [ i, j ].
2883 * 2. The _other_ field has one component. Then
2884 * _this_ [ i, j ] *= _other_ [ i, 0 ].
2886 * The two fields must have same number of tuples and same underlying mesh.
2887 * \param [in] other - an field to multiply to \a this one.
2888 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble, with no nature set.
2889 * The caller is to delete this result field using decrRef() as it is no more
2891 * \throw If \a other is NULL.
2892 * \throw If the fields are not strictly compatible for multiplication
2893 * (areCompatibleForMul()),
2894 * i.e. they differ not only in values and possibly in number of components.
2896 const MEDCouplingFieldDouble &MEDCouplingFieldDouble::operator*=(const MEDCouplingFieldDouble& other)
2898 if(!areCompatibleForMul(&other))
2899 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply *= on them! Check support mesh, and spatial and time discretisation.");
2900 timeDiscr()->multiplyEqual(other.timeDiscr());
2906 * Returns a new MEDCouplingFieldDouble containing division of two given fields.
2907 * There are 2 valid cases.
2908 * 1. The fields have same number of tuples and components. Then each value of
2909 * the result field (_f_) is a division of the corresponding values of \a f1 and
2910 * \a f2, i.e. _f_ [ i, j ] = _f1_ [ i, j ] / _f2_ [ i, j ].
2911 * 2. The fields have same number of tuples and _f2_ has one component. Then
2912 * _f_ [ i, j ] = _f1_ [ i, j ] / _f2_ [ i, 0 ].
2914 * \param [in] f1 - a numerator field.
2915 * \param [in] f2 - a denominator field.
2916 * \return MEDCouplingFieldDouble * - the new instance of MEDCouplingFieldDouble, with no nature set.
2917 * The caller is to delete this result field using decrRef() as it is no more
2919 * \throw If either \a f1 or \a f2 is NULL.
2920 * \throw If the fields are not compatible for division (areCompatibleForDiv()),
2921 * i.e. they differ not only in values and possibly in number of components.
2923 MEDCouplingFieldDouble *MEDCouplingFieldDouble::DivideFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2926 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::DivideFields : input field is NULL !");
2927 if(!f1->areCompatibleForDiv(f2))
2928 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply DivideFields on them! Check support mesh, and spatial and time discretisation.");
2929 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->divide(f2->timeDiscr()));
2930 td->copyTinyAttrFrom(*f1->timeDiscr());
2931 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(NoNature,td,f1->_type->clone()));
2932 ret->setMesh(f1->getMesh());
2937 * Divide values of \a this field by values of another MEDCouplingFieldDouble
2938 * using DataArrayDouble::divideEqual().
2939 * The two fields must have same number of tuples and same underlying mesh.
2940 * There are 2 valid cases.
2941 * 1. The fields have same number of components. Then each value of
2942 * \a this field is divided by the corresponding value of \a other one, i.e.
2943 * _this_ [ i, j ] /= _other_ [ i, j ].
2944 * 2. The \a other field has one component. Then
2945 * _this_ [ i, j ] /= _other_ [ i, 0 ].
2947 * \warning No check of division by zero is performed!
2948 * \param [in] other - an field to divide \a this one by.
2949 * \throw If \a other is NULL.
2950 * \throw If the fields are not compatible for division (areCompatibleForDiv()),
2951 * i.e. they differ not only in values and possibly in number of components.
2953 const MEDCouplingFieldDouble &MEDCouplingFieldDouble::operator/=(const MEDCouplingFieldDouble& other)
2955 if(!areCompatibleForDiv(&other))
2956 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply /= on them! Check support mesh, and spatial and time discretisation.");
2957 timeDiscr()->divideEqual(other.timeDiscr());
2963 * Directly called by MEDCouplingFieldDouble::operator^.
2965 * \sa MEDCouplingFieldDouble::operator^
2967 MEDCouplingFieldDouble *MEDCouplingFieldDouble::PowFields(const MEDCouplingFieldDouble *f1, const MEDCouplingFieldDouble *f2)
2970 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::PowFields : input field is NULL !");
2971 if(!f1->areCompatibleForMul(f2))
2972 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply PowFields on them! Check support mesh, and spatial and time discretisation.");
2973 MEDCouplingTimeDiscretization *td(f1->timeDiscr()->pow(f2->timeDiscr()));
2974 td->copyTinyAttrFrom(*f1->timeDiscr());
2975 MCAuto<MEDCouplingFieldDouble> ret(new MEDCouplingFieldDouble(NoNature,td,f1->_type->clone()));
2976 ret->setMesh(f1->getMesh());
2981 * Directly call MEDCouplingFieldDouble::PowFields static method.
2983 * \sa MEDCouplingFieldDouble::PowFields
2985 MEDCouplingFieldDouble *MEDCouplingFieldDouble::operator^(const MEDCouplingFieldDouble& other) const
2987 return PowFields(this,&other);
2990 const MEDCouplingFieldDouble &MEDCouplingFieldDouble::operator^=(const MEDCouplingFieldDouble& other)
2992 if(!areCompatibleForDiv(&other))
2993 throw INTERP_KERNEL::Exception("Fields are not compatible. Unable to apply ^= on them! Check support mesh, and spatial and time discretisation.");
2994 timeDiscr()->powEqual(other.timeDiscr());
3000 * Writes the field series \a fs and the mesh the fields lie on in the VTK file \a fileName.
3001 * If \a fs is empty no file is written.
3002 * The result file is valid provided that no exception is thrown.
3003 * \warning All the fields must be named and lie on the same non NULL mesh.
3004 * \param [in] fileName - the name of a VTK file to write in.
3005 * \param [in] fs - the fields to write.
3006 * \param [in] isBinary - specifies the VTK format of the written file. By default true (Binary mode)
3007 * \throw If \a fs[ 0 ] == NULL.
3008 * \throw If the fields lie not on the same mesh.
3009 * \throw If the mesh is not set.
3010 * \throw If any of the fields has no name.
3012 * \if ENABLE_EXAMPLES
3013 * \ref cpp_mcfielddouble_WriteVTK "Here is a C++ example".<br>
3014 * \ref py_mcfielddouble_WriteVTK "Here is a Python example".
3017 std::string MEDCouplingFieldDouble::WriteVTK(const std::string& fileName, const std::vector<const MEDCouplingFieldDouble *>& fs, bool isBinary)
3020 return std::string();
3021 std::size_t nfs=fs.size();
3023 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::WriteVTK : 1st instance of field is NULL !");
3024 const MEDCouplingMesh *m=fs[0]->getMesh();
3026 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::WriteVTK : 1st instance of field lies on NULL mesh !");
3027 for(std::size_t i=1;i<nfs;i++)
3028 if(fs[i]->getMesh()!=m)
3029 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::WriteVTK : Fields are not lying on a same mesh ! Expected by VTK ! MEDCouplingFieldDouble::setMesh or MEDCouplingFieldDouble::changeUnderlyingMesh can help to that.");
3031 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::WriteVTK : Fields are lying on a same mesh but it is empty !");
3032 std::string ret(m->getVTKFileNameOf(fileName));
3033 MCAuto<DataArrayByte> byteArr;
3035 { byteArr=DataArrayByte::New(); byteArr->alloc(0,1); }
3036 std::ostringstream coss,noss;
3037 for(std::size_t i=0;i<nfs;i++)
3039 const MEDCouplingFieldDouble *cur=fs[i];
3040 std::string name(cur->getName());
3043 std::ostringstream oss; oss << "MEDCouplingFieldDouble::WriteVTK : Field in pos #" << i << " has no name !";
3044 throw INTERP_KERNEL::Exception(oss.str());
3046 TypeOfField typ=cur->getTypeOfField();
3048 cur->getArray()->writeVTK(coss,8,cur->getName(),byteArr);
3049 else if(typ==ON_NODES)
3050 cur->getArray()->writeVTK(noss,8,cur->getName(),byteArr);
3052 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::WriteVTK : only node and cell fields supported for the moment !");
3054 m->writeVTKAdvanced(ret,coss.str(),noss.str(),byteArr);
3058 MCAuto<MEDCouplingFieldDouble> MEDCouplingFieldDouble::voronoizeGen(const Voronizer *vor, double eps) const
3060 checkConsistencyLight();
3062 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::voronoizeGen : null pointer !");
3063 MCAuto<MEDCouplingFieldDouble> fieldToWO;
3064 const MEDCouplingMesh *inpMeshBase(getMesh());
3065 MCAuto<MEDCouplingUMesh> inpMesh(inpMeshBase->buildUnstructured());
3066 std::string meshName(inpMesh->getName());
3067 if(!inpMesh->isPresenceOfQuadratic())
3068 fieldToWO=clone(false);
3071 fieldToWO=convertQuadraticCellsToLinear();
3072 inpMeshBase=fieldToWO->getMesh();
3073 inpMesh=inpMeshBase->buildUnstructured();
3075 int nbCells(inpMesh->getNumberOfCells());
3076 const MEDCouplingFieldDiscretization *disc(fieldToWO->getDiscretization());
3077 const MEDCouplingFieldDiscretizationGauss *disc2(dynamic_cast<const MEDCouplingFieldDiscretizationGauss *>(disc));
3079 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::voronoize2D : Not a ON_GAUSS_PT field");
3080 int nbLocs(disc2->getNbOfGaussLocalization());
3081 std::vector< MCAuto<MEDCouplingUMesh> > cells(nbCells);
3082 for(int i=0;i<nbLocs;i++)
3084 const MEDCouplingGaussLocalization& gl(disc2->getGaussLocalization(i));
3085 if(gl.getDimension()!=vor->getDimension())
3086 throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::voronoize2D : not a 2D one !");
3087 MCAuto<MEDCouplingUMesh> mesh(gl.buildRefCell());
3088 const std::vector<double>& coo(gl.getGaussCoords());
3089 MCAuto<DataArrayDouble> coo2(DataArrayDouble::NewFromStdVector(coo));
3090 coo2->rearrange(vor->getDimension());
3092 MCAuto<MEDCouplingUMesh> coo3(MEDCouplingUMesh::Build0DMeshFromCoords(coo2));
3094 MCAuto<MEDCouplingUMesh> vorCellsForCurDisc(vor->doIt(mesh,coo2,eps));
3095 std::vector<int> ids;
3096 MCAuto<DataArrayDouble> ptsInReal;
3097 disc2->getCellIdsHavingGaussLocalization(i,ids);
3099 MCAuto<MEDCouplingUMesh> subMesh(inpMesh->buildPartOfMySelf(&ids[0],&ids[0]+ids.size()));
3100 ptsInReal=gl.localizePtsInRefCooForEachCell(vorCellsForCurDisc->getCoords(),subMesh);
3102 int nbPtsPerCell(vorCellsForCurDisc->getNumberOfNodes());
3103 for(std::size_t i=0;i<ids.size();i++)
3105 MCAuto<MEDCouplingUMesh> elt(vorCellsForCurDisc->clone(false));
3106 MCAuto<DataArrayDouble> coo(ptsInReal->selectByTupleIdSafeSlice(i*nbPtsPerCell,(i+1)*nbPtsPerCell,1));
3107 elt->setCoords(coo);
3111 std::vector< const MEDCouplingUMesh * > cellsPtr(VecAutoToVecOfCstPt(cells));
3112 MCAuto<MEDCouplingUMesh> outMesh(MEDCouplingUMesh::MergeUMeshes(cellsPtr));
3113 outMesh->setName(meshName);
3114 MCAuto<MEDCouplingFieldDouble> onCells(MEDCouplingFieldDouble::New(ON_CELLS));
3115 onCells->setMesh(outMesh);
3117 MCAuto<DataArrayDouble> arr(fieldToWO->getArray()->deepCopy());
3118 onCells->setArray(arr);
3120 onCells->setTimeUnit(getTimeUnit());
3123 double a(getTime(b,c));
3124 onCells->setTime(a,b,c);
3126 onCells->setName(getName());
3130 MEDCouplingTimeDiscretization *MEDCouplingFieldDouble::timeDiscr()
3132 MEDCouplingTimeDiscretizationTemplate<double> *ret(_time_discr);
3135 MEDCouplingTimeDiscretization *retc(dynamic_cast<MEDCouplingTimeDiscretization *>(ret));
3137 throw INTERP_KERNEL::Exception("Field Double Null invalid type of time discr !");
3141 const MEDCouplingTimeDiscretization *MEDCouplingFieldDouble::timeDiscr() const
3143 const MEDCouplingTimeDiscretizationTemplate<double> *ret(_time_discr);
3146 const MEDCouplingTimeDiscretization *retc(dynamic_cast<const MEDCouplingTimeDiscretization *>(ret));
3148 throw INTERP_KERNEL::Exception("Field Double Null invalid type of time discr !");