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 "MEDCouplingMemArray.txx"
24 #include "GenMathFormulae.hxx"
25 #include "InterpKernelAutoPtr.hxx"
26 #include "InterpKernelExprParser.hxx"
35 typedef double (*MYFUNCPTR)(double);
37 using namespace MEDCoupling;
39 template class MEDCoupling::MemArray<int>;
40 template class MEDCoupling::MemArray<double>;
41 template class MEDCoupling::DataArrayTemplate<int>;
42 template class MEDCoupling::DataArrayTemplate<double>;
43 template class MEDCoupling::DataArrayTemplateClassic<int>;
44 template class MEDCoupling::DataArrayTemplateClassic<double>;
45 template class MEDCoupling::DataArrayTemplateFP<double>;
46 template class MEDCoupling::DataArrayIterator<double>;
47 template class MEDCoupling::DataArrayIterator<int>;
49 template<int SPACEDIM>
50 void DataArrayDouble::findCommonTuplesAlg(const double *bbox, int nbNodes, int limitNodeId, double prec, DataArrayInt *c, DataArrayInt *cI) const
52 const double *coordsPtr=getConstPointer();
53 BBTreePts<SPACEDIM,int> myTree(bbox,0,0,nbNodes,prec);
54 std::vector<bool> isDone(nbNodes);
55 for(int i=0;i<nbNodes;i++)
59 std::vector<int> intersectingElems;
60 myTree.getElementsAroundPoint(coordsPtr+i*SPACEDIM,intersectingElems);
61 if(intersectingElems.size()>1)
63 std::vector<int> commonNodes;
64 for(std::vector<int>::const_iterator it=intersectingElems.begin();it!=intersectingElems.end();it++)
68 commonNodes.push_back(*it);
71 if(!commonNodes.empty())
73 cI->pushBackSilent(cI->back()+(int)commonNodes.size()+1);
75 c->insertAtTheEnd(commonNodes.begin(),commonNodes.end());
82 template<int SPACEDIM>
83 void DataArrayDouble::FindTupleIdsNearTuplesAlg(const BBTreePts<SPACEDIM,int>& myTree, const double *pos, int nbOfTuples, double eps,
84 DataArrayInt *c, DataArrayInt *cI)
86 for(int i=0;i<nbOfTuples;i++)
88 std::vector<int> intersectingElems;
89 myTree.getElementsAroundPoint(pos+i*SPACEDIM,intersectingElems);
90 std::vector<int> commonNodes;
91 for(std::vector<int>::const_iterator it=intersectingElems.begin();it!=intersectingElems.end();it++)
92 commonNodes.push_back(*it);
93 cI->pushBackSilent(cI->back()+(int)commonNodes.size());
94 c->insertAtTheEnd(commonNodes.begin(),commonNodes.end());
98 template<int SPACEDIM>
99 void DataArrayDouble::FindClosestTupleIdAlg(const BBTreePts<SPACEDIM,int>& myTree, double dist, const double *pos, int nbOfTuples, const double *thisPt, int thisNbOfTuples, int *res)
101 double distOpt(dist);
102 const double *p(pos);
104 for(int i=0;i<nbOfTuples;i++,p+=SPACEDIM,r++)
109 double ret=myTree.getElementsAroundPoint2(p,distOpt,elem);
110 if(ret!=std::numeric_limits<double>::max())
112 distOpt=std::max(ret,1e-4);
117 { distOpt=2*distOpt; continue; }
122 int DataArray::EffectiveCircPerm(int nbOfShift, int nbOfTuples)
125 throw INTERP_KERNEL::Exception("DataArray::EffectiveCircPerm : number of tuples is expected to be > 0 !");
128 return nbOfShift%nbOfTuples;
134 return nbOfTuples-tmp;
138 std::size_t DataArray::getHeapMemorySizeWithoutChildren() const
140 std::size_t sz1=_name.capacity();
141 std::size_t sz2=_info_on_compo.capacity();
143 for(std::vector<std::string>::const_iterator it=_info_on_compo.begin();it!=_info_on_compo.end();it++)
144 sz3+=(*it).capacity();
148 std::vector<const BigMemoryObject *> DataArray::getDirectChildrenWithNull() const
150 return std::vector<const BigMemoryObject *>();
154 * Sets the attribute \a _name of \a this array.
155 * See \ref MEDCouplingArrayBasicsName "DataArrays infos" for more information.
156 * \param [in] name - new array name
158 void DataArray::setName(const std::string& name)
164 * Copies textual data from an \a other DataArray. The copied data are
165 * - the name attribute,
166 * - the information of components.
168 * For more information on these data see \ref MEDCouplingArrayBasicsName "DataArrays infos".
170 * \param [in] other - another instance of DataArray to copy the textual data from.
171 * \throw If number of components of \a this array differs from that of the \a other.
173 void DataArray::copyStringInfoFrom(const DataArray& other)
175 if(_info_on_compo.size()!=other._info_on_compo.size())
176 throw INTERP_KERNEL::Exception("Size of arrays mismatches on copyStringInfoFrom !");
178 _info_on_compo=other._info_on_compo;
181 void DataArray::copyPartOfStringInfoFrom(const DataArray& other, const std::vector<int>& compoIds)
183 int nbOfCompoOth=other.getNumberOfComponents();
184 std::size_t newNbOfCompo=compoIds.size();
185 for(std::size_t i=0;i<newNbOfCompo;i++)
186 if(compoIds[i]>=nbOfCompoOth || compoIds[i]<0)
188 std::ostringstream oss; oss << "Specified component id is out of range (" << compoIds[i] << ") compared with nb of actual components (" << nbOfCompoOth << ")";
189 throw INTERP_KERNEL::Exception(oss.str().c_str());
191 for(std::size_t i=0;i<newNbOfCompo;i++)
192 setInfoOnComponent((int)i,other.getInfoOnComponent(compoIds[i]));
195 void DataArray::copyPartOfStringInfoFrom2(const std::vector<int>& compoIds, const DataArray& other)
197 int nbOfCompo=getNumberOfComponents();
198 std::size_t partOfCompoToSet=compoIds.size();
199 if((int)partOfCompoToSet!=other.getNumberOfComponents())
200 throw INTERP_KERNEL::Exception("Given compoIds has not the same size as number of components of given array !");
201 for(std::size_t i=0;i<partOfCompoToSet;i++)
202 if(compoIds[i]>=nbOfCompo || compoIds[i]<0)
204 std::ostringstream oss; oss << "Specified component id is out of range (" << compoIds[i] << ") compared with nb of actual components (" << nbOfCompo << ")";
205 throw INTERP_KERNEL::Exception(oss.str().c_str());
207 for(std::size_t i=0;i<partOfCompoToSet;i++)
208 setInfoOnComponent(compoIds[i],other.getInfoOnComponent((int)i));
211 bool DataArray::areInfoEqualsIfNotWhy(const DataArray& other, std::string& reason) const
213 std::ostringstream oss;
214 if(_name!=other._name)
216 oss << "Names DataArray mismatch : this name=\"" << _name << " other name=\"" << other._name << "\" !";
220 if(_info_on_compo!=other._info_on_compo)
222 oss << "Components DataArray mismatch : \nThis components=";
223 for(std::vector<std::string>::const_iterator it=_info_on_compo.begin();it!=_info_on_compo.end();it++)
224 oss << "\"" << *it << "\",";
225 oss << "\nOther components=";
226 for(std::vector<std::string>::const_iterator it=other._info_on_compo.begin();it!=other._info_on_compo.end();it++)
227 oss << "\"" << *it << "\",";
235 * Compares textual information of \a this DataArray with that of an \a other one.
236 * The compared data are
237 * - the name attribute,
238 * - the information of components.
240 * For more information on these data see \ref MEDCouplingArrayBasicsName "DataArrays infos".
241 * \param [in] other - another instance of DataArray to compare the textual data of.
242 * \return bool - \a true if the textual information is same, \a false else.
244 bool DataArray::areInfoEquals(const DataArray& other) const
247 return areInfoEqualsIfNotWhy(other,tmp);
250 void DataArray::reprWithoutNameStream(std::ostream& stream) const
252 stream << "Number of components : "<< getNumberOfComponents() << "\n";
253 stream << "Info of these components : ";
254 for(std::vector<std::string>::const_iterator iter=_info_on_compo.begin();iter!=_info_on_compo.end();iter++)
255 stream << "\"" << *iter << "\" ";
259 std::string DataArray::cppRepr(const std::string& varName) const
261 std::ostringstream ret;
262 reprCppStream(varName,ret);
267 * Sets information on all components. To know more on format of this information
268 * see \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
269 * \param [in] info - a vector of strings.
270 * \throw If size of \a info differs from the number of components of \a this.
272 void DataArray::setInfoOnComponents(const std::vector<std::string>& info)
274 if(getNumberOfComponents()!=(int)info.size())
276 std::ostringstream oss; oss << "DataArray::setInfoOnComponents : input is of size " << info.size() << " whereas number of components is equal to " << getNumberOfComponents() << " !";
277 throw INTERP_KERNEL::Exception(oss.str().c_str());
283 * This method is only a dispatcher towards DataArrayDouble::setPartOfValues3, DataArrayInt::setPartOfValues3, DataArrayChar::setPartOfValues3 depending on the true
284 * type of \a this and \a aBase.
286 * \throw If \a aBase and \a this do not have the same type.
288 * \sa DataArrayDouble::setPartOfValues3, DataArrayInt::setPartOfValues3, DataArrayChar::setPartOfValues3.
290 void DataArray::setPartOfValuesBase3(const DataArray *aBase, const int *bgTuples, const int *endTuples, int bgComp, int endComp, int stepComp, bool strictCompoCompare)
293 throw INTERP_KERNEL::Exception("DataArray::setPartOfValuesBase3 : input aBase object is NULL !");
294 DataArrayDouble *this1(dynamic_cast<DataArrayDouble *>(this));
295 DataArrayInt *this2(dynamic_cast<DataArrayInt *>(this));
296 DataArrayChar *this3(dynamic_cast<DataArrayChar *>(this));
297 const DataArrayDouble *a1(dynamic_cast<const DataArrayDouble *>(aBase));
298 const DataArrayInt *a2(dynamic_cast<const DataArrayInt *>(aBase));
299 const DataArrayChar *a3(dynamic_cast<const DataArrayChar *>(aBase));
302 this1->setPartOfValues3(a1,bgTuples,endTuples,bgComp,endComp,stepComp,strictCompoCompare);
307 this2->setPartOfValues3(a2,bgTuples,endTuples,bgComp,endComp,stepComp,strictCompoCompare);
312 this3->setPartOfValues3(a3,bgTuples,endTuples,bgComp,endComp,stepComp,strictCompoCompare);
315 throw INTERP_KERNEL::Exception("DataArray::setPartOfValuesBase3 : input aBase object and this do not have the same type !");
318 std::vector<std::string> DataArray::getVarsOnComponent() const
320 int nbOfCompo=(int)_info_on_compo.size();
321 std::vector<std::string> ret(nbOfCompo);
322 for(int i=0;i<nbOfCompo;i++)
323 ret[i]=getVarOnComponent(i);
327 std::vector<std::string> DataArray::getUnitsOnComponent() const
329 int nbOfCompo=(int)_info_on_compo.size();
330 std::vector<std::string> ret(nbOfCompo);
331 for(int i=0;i<nbOfCompo;i++)
332 ret[i]=getUnitOnComponent(i);
337 * Returns information on a component specified by an index.
338 * To know more on format of this information
339 * see \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
340 * \param [in] i - the index (zero based) of the component of interest.
341 * \return std::string - a string containing the information on \a i-th component.
342 * \throw If \a i is not a valid component index.
344 std::string DataArray::getInfoOnComponent(int i) const
346 if(i<(int)_info_on_compo.size() && i>=0)
347 return _info_on_compo[i];
350 std::ostringstream oss; oss << "DataArray::getInfoOnComponent : Specified component id is out of range (" << i << ") compared with nb of actual components (" << (int) _info_on_compo.size();
351 throw INTERP_KERNEL::Exception(oss.str().c_str());
356 * Returns the var part of the full information of the \a i-th component.
357 * For example, if \c getInfoOnComponent(0) returns "SIGXY [N/m^2]", then
358 * \c getVarOnComponent(0) returns "SIGXY".
359 * If a unit part of information is not detected by presence of
360 * two square brackets, then the full information is returned.
361 * To read more about the component information format, see
362 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
363 * \param [in] i - the index (zero based) of the component of interest.
364 * \return std::string - a string containing the var information, or the full info.
365 * \throw If \a i is not a valid component index.
367 std::string DataArray::getVarOnComponent(int i) const
369 if(i<(int)_info_on_compo.size() && i>=0)
371 return GetVarNameFromInfo(_info_on_compo[i]);
375 std::ostringstream oss; oss << "DataArray::getVarOnComponent : Specified component id is out of range (" << i << ") compared with nb of actual components (" << (int) _info_on_compo.size();
376 throw INTERP_KERNEL::Exception(oss.str().c_str());
381 * Returns the unit part of the full information of the \a i-th component.
382 * For example, if \c getInfoOnComponent(0) returns "SIGXY [ N/m^2]", then
383 * \c getUnitOnComponent(0) returns " N/m^2".
384 * If a unit part of information is not detected by presence of
385 * two square brackets, then an empty string is returned.
386 * To read more about the component information format, see
387 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
388 * \param [in] i - the index (zero based) of the component of interest.
389 * \return std::string - a string containing the unit information, if any, or "".
390 * \throw If \a i is not a valid component index.
392 std::string DataArray::getUnitOnComponent(int i) const
394 if(i<(int)_info_on_compo.size() && i>=0)
396 return GetUnitFromInfo(_info_on_compo[i]);
400 std::ostringstream oss; oss << "DataArray::getUnitOnComponent : Specified component id is out of range (" << i << ") compared with nb of actual components (" << (int) _info_on_compo.size();
401 throw INTERP_KERNEL::Exception(oss.str().c_str());
406 * Returns the var part of the full component information.
407 * For example, if \a info == "SIGXY [N/m^2]", then this method returns "SIGXY".
408 * If a unit part of information is not detected by presence of
409 * two square brackets, then the whole \a info is returned.
410 * To read more about the component information format, see
411 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
412 * \param [in] info - the full component information.
413 * \return std::string - a string containing only var information, or the \a info.
415 std::string DataArray::GetVarNameFromInfo(const std::string& info)
417 std::size_t p1=info.find_last_of('[');
418 std::size_t p2=info.find_last_of(']');
419 if(p1==std::string::npos || p2==std::string::npos)
424 return std::string();
425 std::size_t p3=info.find_last_not_of(' ',p1-1);
426 return info.substr(0,p3+1);
430 * Returns the unit part of the full component information.
431 * For example, if \a info == "SIGXY [ N/m^2]", then this method returns " N/m^2".
432 * If a unit part of information is not detected by presence of
433 * two square brackets, then an empty string is returned.
434 * To read more about the component information format, see
435 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
436 * \param [in] info - the full component information.
437 * \return std::string - a string containing only unit information, if any, or "".
439 std::string DataArray::GetUnitFromInfo(const std::string& info)
441 std::size_t p1=info.find_last_of('[');
442 std::size_t p2=info.find_last_of(']');
443 if(p1==std::string::npos || p2==std::string::npos)
444 return std::string();
446 return std::string();
447 return info.substr(p1+1,p2-p1-1);
451 * This method put in info format the result of the merge of \a var and \a unit.
452 * The standard format for that is "var [unit]".
453 * Inversely you can retrieve the var part or the unit part of info string using resp. GetVarNameFromInfo and GetUnitFromInfo.
455 std::string DataArray::BuildInfoFromVarAndUnit(const std::string& var, const std::string& unit)
457 std::ostringstream oss;
458 oss << var << " [" << unit << "]";
462 std::string DataArray::GetAxisTypeRepr(MEDCouplingAxisType at)
467 return std::string("AX_CART");
469 return std::string("AX_CYL");
471 return std::string("AX_SPHER");
473 throw INTERP_KERNEL::Exception("DataArray::GetAxisTypeRepr : unrecognized axis type enum !");
478 * Returns a new DataArray by concatenating all given arrays, so that (1) the number
479 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
480 * the number of component in the result array is same as that of each of given arrays.
481 * Info on components is copied from the first of the given arrays. Number of components
482 * in the given arrays must be the same.
483 * \param [in] arrs - a sequence of arrays to include in the result array. All arrays must have the same type.
484 * \return DataArray * - the new instance of DataArray (that can be either DataArrayInt, DataArrayDouble, DataArrayChar).
485 * The caller is to delete this result array using decrRef() as it is no more
487 * \throw If all arrays within \a arrs are NULL.
488 * \throw If all not null arrays in \a arrs have not the same type.
489 * \throw If getNumberOfComponents() of arrays within \a arrs.
491 DataArray *DataArray::Aggregate(const std::vector<const DataArray *>& arrs)
493 std::vector<const DataArray *> arr2;
494 for(std::vector<const DataArray *>::const_iterator it=arrs.begin();it!=arrs.end();it++)
498 throw INTERP_KERNEL::Exception("DataArray::Aggregate : only null instance in input vector !");
499 std::vector<const DataArrayDouble *> arrd;
500 std::vector<const DataArrayInt *> arri;
501 std::vector<const DataArrayChar *> arrc;
502 for(std::vector<const DataArray *>::const_iterator it=arr2.begin();it!=arr2.end();it++)
504 const DataArrayDouble *a=dynamic_cast<const DataArrayDouble *>(*it);
506 { arrd.push_back(a); continue; }
507 const DataArrayInt *b=dynamic_cast<const DataArrayInt *>(*it);
509 { arri.push_back(b); continue; }
510 const DataArrayChar *c=dynamic_cast<const DataArrayChar *>(*it);
512 { arrc.push_back(c); continue; }
513 throw INTERP_KERNEL::Exception("DataArray::Aggregate : presence of not null instance in inuput that is not in [DataArrayDouble, DataArrayInt, DataArrayChar] !");
515 if(arr2.size()==arrd.size())
516 return DataArrayDouble::Aggregate(arrd);
517 if(arr2.size()==arri.size())
518 return DataArrayInt::Aggregate(arri);
519 if(arr2.size()==arrc.size())
520 return DataArrayChar::Aggregate(arrc);
521 throw INTERP_KERNEL::Exception("DataArray::Aggregate : all input arrays must have the same type !");
525 * Sets information on a component specified by an index.
526 * To know more on format of this information
527 * see \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
528 * \warning Don't pass NULL as \a info!
529 * \param [in] i - the index (zero based) of the component of interest.
530 * \param [in] info - the string containing the information.
531 * \throw If \a i is not a valid component index.
533 void DataArray::setInfoOnComponent(int i, const std::string& info)
535 if(i<(int)_info_on_compo.size() && i>=0)
536 _info_on_compo[i]=info;
539 std::ostringstream oss; oss << "DataArray::setInfoOnComponent : Specified component id is out of range (" << i << ") compared with nb of actual components (" << (int) _info_on_compo.size();
540 throw INTERP_KERNEL::Exception(oss.str().c_str());
545 * Sets information on all components. This method can change number of components
546 * at certain conditions; if the conditions are not respected, an exception is thrown.
547 * The number of components can be changed in \a this only if \a this is not allocated.
548 * The condition of number of components must not be changed.
550 * To know more on format of the component information see
551 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
552 * \param [in] info - a vector of component infos.
553 * \throw If \a this->getNumberOfComponents() != \a info.size() && \a this->isAllocated()
555 void DataArray::setInfoAndChangeNbOfCompo(const std::vector<std::string>& info)
557 if(getNumberOfComponents()!=(int)info.size())
563 std::ostringstream oss; oss << "DataArray::setInfoAndChangeNbOfCompo : input is of size " << info.size() << " whereas number of components is equal to " << getNumberOfComponents() << " and this is already allocated !";
564 throw INTERP_KERNEL::Exception(oss.str().c_str());
571 void DataArray::checkNbOfTuples(int nbOfTuples, const std::string& msg) const
573 if(getNumberOfTuples()!=nbOfTuples)
575 std::ostringstream oss; oss << msg << " : mismatch number of tuples : expected " << nbOfTuples << " having " << getNumberOfTuples() << " !";
576 throw INTERP_KERNEL::Exception(oss.str().c_str());
580 void DataArray::checkNbOfComps(int nbOfCompo, const std::string& msg) const
582 if(getNumberOfComponents()!=nbOfCompo)
584 std::ostringstream oss; oss << msg << " : mismatch number of components : expected " << nbOfCompo << " having " << getNumberOfComponents() << " !";
585 throw INTERP_KERNEL::Exception(oss.str().c_str());
589 void DataArray::checkNbOfElems(std::size_t nbOfElems, const std::string& msg) const
591 if(getNbOfElems()!=nbOfElems)
593 std::ostringstream oss; oss << msg << " : mismatch number of elems : Expected " << nbOfElems << " having " << getNbOfElems() << " !";
594 throw INTERP_KERNEL::Exception(oss.str().c_str());
598 void DataArray::checkNbOfTuplesAndComp(const DataArray& other, const std::string& msg) const
600 if(getNumberOfTuples()!=other.getNumberOfTuples())
602 std::ostringstream oss; oss << msg << " : mismatch number of tuples : expected " << other.getNumberOfTuples() << " having " << getNumberOfTuples() << " !";
603 throw INTERP_KERNEL::Exception(oss.str().c_str());
605 if(getNumberOfComponents()!=other.getNumberOfComponents())
607 std::ostringstream oss; oss << msg << " : mismatch number of components : expected " << other.getNumberOfComponents() << " having " << getNumberOfComponents() << " !";
608 throw INTERP_KERNEL::Exception(oss.str().c_str());
612 void DataArray::checkNbOfTuplesAndComp(int nbOfTuples, int nbOfCompo, const std::string& msg) const
614 checkNbOfTuples(nbOfTuples,msg);
615 checkNbOfComps(nbOfCompo,msg);
619 * Simply this method checks that \b value is in [0,\b ref).
621 void DataArray::CheckValueInRange(int ref, int value, const std::string& msg)
623 if(value<0 || value>=ref)
625 std::ostringstream oss; oss << "DataArray::CheckValueInRange : " << msg << " ! Expected in range [0," << ref << "[ having " << value << " !";
626 throw INTERP_KERNEL::Exception(oss.str().c_str());
631 * This method checks that [\b start, \b end) is compliant with ref length \b value.
632 * typicaly start in [0,\b value) and end in [0,\b value). If value==start and start==end, it is supported.
634 void DataArray::CheckValueInRangeEx(int value, int start, int end, const std::string& msg)
636 if(start<0 || start>=value)
638 if(value!=start || end!=start)
640 std::ostringstream oss; oss << "DataArray::CheckValueInRangeEx : " << msg << " ! Expected start " << start << " of input range, in [0," << value << "[ !";
641 throw INTERP_KERNEL::Exception(oss.str().c_str());
644 if(end<0 || end>value)
646 std::ostringstream oss; oss << "DataArray::CheckValueInRangeEx : " << msg << " ! Expected end " << end << " of input range, in [0," << value << "] !";
647 throw INTERP_KERNEL::Exception(oss.str().c_str());
651 void DataArray::CheckClosingParInRange(int ref, int value, const std::string& msg)
653 if(value<0 || value>ref)
655 std::ostringstream oss; oss << "DataArray::CheckClosingParInRange : " << msg << " ! Expected input range in [0," << ref << "] having closing open parenthesis " << value << " !";
656 throw INTERP_KERNEL::Exception(oss.str().c_str());
661 * This method is useful to slice work among a pool of threads or processes. \a begin, \a end \a step is the input whole slice of work to perform,
662 * typically it is a whole slice of tuples of DataArray or cells, nodes of a mesh...
664 * The input \a sliceId should be an id in [0, \a nbOfSlices) that specifies the slice of work.
666 * \param [in] start - the start of the input slice of the whole work to perform splitted into slices.
667 * \param [in] stop - the stop of the input slice of the whole work to perform splitted into slices.
668 * \param [in] step - the step (that can be <0) of the input slice of the whole work to perform splitted into slices.
669 * \param [in] sliceId - the slice id considered
670 * \param [in] nbOfSlices - the number of slices (typically the number of cores on which the work is expected to be sliced)
671 * \param [out] startSlice - the start of the slice considered
672 * \param [out] stopSlice - the stop of the slice consided
674 * \throw If \a step == 0
675 * \throw If \a nbOfSlices not > 0
676 * \throw If \a sliceId not in [0,nbOfSlices)
678 void DataArray::GetSlice(int start, int stop, int step, int sliceId, int nbOfSlices, int& startSlice, int& stopSlice)
682 std::ostringstream oss; oss << "DataArray::GetSlice : nbOfSlices (" << nbOfSlices << ") must be > 0 !";
683 throw INTERP_KERNEL::Exception(oss.str().c_str());
685 if(sliceId<0 || sliceId>=nbOfSlices)
687 std::ostringstream oss; oss << "DataArray::GetSlice : sliceId (" << nbOfSlices << ") must be in [0 , nbOfSlices (" << nbOfSlices << ") ) !";
688 throw INTERP_KERNEL::Exception(oss.str().c_str());
690 int nbElems=GetNumberOfItemGivenBESRelative(start,stop,step,"DataArray::GetSlice");
691 int minNbOfElemsPerSlice=nbElems/nbOfSlices;
692 startSlice=start+minNbOfElemsPerSlice*step*sliceId;
693 if(sliceId<nbOfSlices-1)
694 stopSlice=start+minNbOfElemsPerSlice*step*(sliceId+1);
699 int DataArray::GetNumberOfItemGivenBES(int begin, int end, int step, const std::string& msg)
703 std::ostringstream oss; oss << msg << " : end before begin !";
704 throw INTERP_KERNEL::Exception(oss.str().c_str());
710 std::ostringstream oss; oss << msg << " : invalid step should be > 0 !";
711 throw INTERP_KERNEL::Exception(oss.str().c_str());
713 return (end-1-begin)/step+1;
716 int DataArray::GetNumberOfItemGivenBESRelative(int begin, int end, int step, const std::string& msg)
719 throw INTERP_KERNEL::Exception("DataArray::GetNumberOfItemGivenBES : step=0 is not allowed !");
720 if(end<begin && step>0)
722 std::ostringstream oss; oss << msg << " : end before begin whereas step is positive !";
723 throw INTERP_KERNEL::Exception(oss.str().c_str());
725 if(begin<end && step<0)
727 std::ostringstream oss; oss << msg << " : invalid step should be > 0 !";
728 throw INTERP_KERNEL::Exception(oss.str().c_str());
731 return (std::max(begin,end)-1-std::min(begin,end))/std::abs(step)+1;
736 int DataArray::GetPosOfItemGivenBESRelativeNoThrow(int value, int begin, int end, int step)
742 if(begin<=value && value<end)
744 if((value-begin)%step==0)
745 return (value-begin)/step;
754 if(begin>=value && value>end)
756 if((begin-value)%(-step)==0)
757 return (begin-value)/(-step);
770 * Returns a new instance of DataArrayDouble. The caller is to delete this array
771 * using decrRef() as it is no more needed.
773 DataArrayDouble *DataArrayDouble::New()
775 return new DataArrayDouble;
779 * Returns the only one value in \a this, if and only if number of elements
780 * (nb of tuples * nb of components) is equal to 1, and that \a this is allocated.
781 * \return double - the sole value stored in \a this array.
782 * \throw If at least one of conditions stated above is not fulfilled.
784 double DataArrayDouble::doubleValue() const
788 if(getNbOfElems()==1)
790 return *getConstPointer();
793 throw INTERP_KERNEL::Exception("DataArrayDouble::doubleValue : DataArrayDouble instance is allocated but number of elements is not equal to 1 !");
796 throw INTERP_KERNEL::Exception("DataArrayDouble::doubleValue : DataArrayDouble instance is not allocated !");
800 * Returns a full copy of \a this. For more info on copying data arrays see
801 * \ref MEDCouplingArrayBasicsCopyDeep.
802 * \return DataArrayDouble * - a new instance of DataArrayDouble. The caller is to
803 * delete this array using decrRef() as it is no more needed.
805 DataArrayDouble *DataArrayDouble::deepCopy() const
807 return new DataArrayDouble(*this);
811 * Returns either a \a deep or \a shallow copy of this array. For more info see
812 * \ref MEDCouplingArrayBasicsCopyDeep and \ref MEDCouplingArrayBasicsCopyShallow.
813 * \param [in] dCpy - if \a true, a deep copy is returned, else, a shallow one.
814 * \return DataArrayDouble * - either a new instance of DataArrayDouble (if \a dCpy
815 * == \a true) or \a this instance (if \a dCpy == \a false).
817 DataArrayDouble *DataArrayDouble::performCopyOrIncrRef(bool dCpy) const
819 return DataArrayTemplateClassic<double>::PerformCopyOrIncrRef(dCpy,*this);
823 * Assign zero to all values in \a this array. To know more on filling arrays see
824 * \ref MEDCouplingArrayFill.
825 * \throw If \a this is not allocated.
827 void DataArrayDouble::fillWithZero()
833 * Checks that \a this array is consistently **increasing** or **decreasing** in value,
834 * with at least absolute difference value of |\a eps| at each step.
835 * If not an exception is thrown.
836 * \param [in] increasing - if \a true, the array values should be increasing.
837 * \param [in] eps - minimal absolute difference between the neighbor values at which
838 * the values are considered different.
839 * \throw If sequence of values is not strictly monotonic in agreement with \a
841 * \throw If \a this->getNumberOfComponents() != 1.
842 * \throw If \a this is not allocated.
844 void DataArrayDouble::checkMonotonic(bool increasing, double eps) const
846 if(!isMonotonic(increasing,eps))
849 throw INTERP_KERNEL::Exception("DataArrayDouble::checkMonotonic : 'this' is not INCREASING monotonic !");
851 throw INTERP_KERNEL::Exception("DataArrayDouble::checkMonotonic : 'this' is not DECREASING monotonic !");
856 * Checks that \a this array is consistently **increasing** or **decreasing** in value,
857 * with at least absolute difference value of |\a eps| at each step.
858 * \param [in] increasing - if \a true, array values should be increasing.
859 * \param [in] eps - minimal absolute difference between the neighbor values at which
860 * the values are considered different.
861 * \return bool - \a true if values change in accordance with \a increasing arg.
862 * \throw If \a this->getNumberOfComponents() != 1.
863 * \throw If \a this is not allocated.
865 bool DataArrayDouble::isMonotonic(bool increasing, double eps) const
868 if(getNumberOfComponents()!=1)
869 throw INTERP_KERNEL::Exception("DataArrayDouble::isMonotonic : only supported with 'this' array with ONE component !");
870 int nbOfElements=getNumberOfTuples();
871 const double *ptr=getConstPointer();
875 double absEps=fabs(eps);
878 for(int i=1;i<nbOfElements;i++)
880 if(ptr[i]<(ref+absEps))
888 for(int i=1;i<nbOfElements;i++)
890 if(ptr[i]>(ref-absEps))
899 * Returns a textual and human readable representation of \a this instance of
900 * DataArrayDouble. This text is shown when a DataArrayDouble is printed in Python.
901 * \return std::string - text describing \a this DataArrayDouble.
903 * \sa reprNotTooLong, reprZip
905 std::string DataArrayDouble::repr() const
907 std::ostringstream ret;
912 std::string DataArrayDouble::reprZip() const
914 std::ostringstream ret;
920 * This method is close to repr method except that when \a this has more than 1000 tuples, all tuples are not
921 * printed out to avoid to consume too much space in interpretor.
924 std::string DataArrayDouble::reprNotTooLong() const
926 std::ostringstream ret;
927 reprNotTooLongStream(ret);
931 void DataArrayDouble::writeVTK(std::ostream& ofs, int indent, const std::string& nameInFile, DataArrayByte *byteArr) const
933 static const char SPACE[4]={' ',' ',' ',' '};
935 std::string idt(indent,' ');
937 ofs << idt << "<DataArray type=\"Float32\" Name=\"" << nameInFile << "\" NumberOfComponents=\"" << getNumberOfComponents() << "\"";
939 bool areAllEmpty(true);
940 for(std::vector<std::string>::const_iterator it=_info_on_compo.begin();it!=_info_on_compo.end();it++)
944 for(std::size_t i=0;i<_info_on_compo.size();i++)
945 ofs << " ComponentName" << i << "=\"" << _info_on_compo[i] << "\"";
949 ofs << " format=\"appended\" offset=\"" << byteArr->getNumberOfTuples() << "\">";
950 INTERP_KERNEL::AutoPtr<float> tmp(new float[getNbOfElems()]);
952 // to make Visual C++ happy : instead of std::copy(begin(),end(),(float *)tmp);
953 for(const double *src=begin();src!=end();src++,pt++)
955 const char *data(reinterpret_cast<const char *>((float *)tmp));
956 std::size_t sz(getNbOfElems()*sizeof(float));
957 byteArr->insertAtTheEnd(data,data+sz);
958 byteArr->insertAtTheEnd(SPACE,SPACE+4);
962 ofs << " RangeMin=\"" << getMinValueInArray() << "\" RangeMax=\"" << getMaxValueInArray() << "\" format=\"ascii\">\n" << idt;
963 std::copy(begin(),end(),std::ostream_iterator<double>(ofs," "));
965 ofs << std::endl << idt << "</DataArray>\n";
968 void DataArrayDouble::reprStream(std::ostream& stream) const
970 stream << "Name of double array : \"" << _name << "\"\n";
971 reprWithoutNameStream(stream);
974 void DataArrayDouble::reprZipStream(std::ostream& stream) const
976 stream << "Name of double array : \"" << _name << "\"\n";
977 reprZipWithoutNameStream(stream);
980 void DataArrayDouble::reprNotTooLongStream(std::ostream& stream) const
982 stream << "Name of double array : \"" << _name << "\"\n";
983 reprNotTooLongWithoutNameStream(stream);
986 void DataArrayDouble::reprWithoutNameStream(std::ostream& stream) const
988 DataArray::reprWithoutNameStream(stream);
989 stream.precision(17);
990 _mem.repr(getNumberOfComponents(),stream);
993 void DataArrayDouble::reprZipWithoutNameStream(std::ostream& stream) const
995 DataArray::reprWithoutNameStream(stream);
996 stream.precision(17);
997 _mem.reprZip(getNumberOfComponents(),stream);
1000 void DataArrayDouble::reprNotTooLongWithoutNameStream(std::ostream& stream) const
1002 DataArray::reprWithoutNameStream(stream);
1003 stream.precision(17);
1004 _mem.reprNotTooLong(getNumberOfComponents(),stream);
1007 void DataArrayDouble::reprCppStream(const std::string& varName, std::ostream& stream) const
1009 int nbTuples(getNumberOfTuples()),nbComp(getNumberOfComponents());
1010 const double *data(getConstPointer());
1011 stream.precision(17);
1012 stream << "DataArrayDouble *" << varName << "=DataArrayDouble::New();" << std::endl;
1013 if(nbTuples*nbComp>=1)
1015 stream << "const double " << varName << "Data[" << nbTuples*nbComp << "]={";
1016 std::copy(data,data+nbTuples*nbComp-1,std::ostream_iterator<double>(stream,","));
1017 stream << data[nbTuples*nbComp-1] << "};" << std::endl;
1018 stream << varName << "->useArray(" << varName << "Data,false,CPP_DEALLOC," << nbTuples << "," << nbComp << ");" << std::endl;
1021 stream << varName << "->alloc(" << nbTuples << "," << nbComp << ");" << std::endl;
1022 stream << varName << "->setName(\"" << getName() << "\");" << std::endl;
1026 * Method that gives a quick overvien of \a this for python.
1028 void DataArrayDouble::reprQuickOverview(std::ostream& stream) const
1030 static const std::size_t MAX_NB_OF_BYTE_IN_REPR=300;
1031 stream << "DataArrayDouble C++ instance at " << this << ". ";
1034 int nbOfCompo=(int)_info_on_compo.size();
1037 int nbOfTuples=getNumberOfTuples();
1038 stream << "Number of tuples : " << nbOfTuples << ". Number of components : " << nbOfCompo << "." << std::endl;
1039 reprQuickOverviewData(stream,MAX_NB_OF_BYTE_IN_REPR);
1042 stream << "Number of components : 0.";
1045 stream << "*** No data allocated ****";
1048 void DataArrayDouble::reprQuickOverviewData(std::ostream& stream, std::size_t maxNbOfByteInRepr) const
1050 const double *data=begin();
1051 int nbOfTuples=getNumberOfTuples();
1052 int nbOfCompo=(int)_info_on_compo.size();
1053 std::ostringstream oss2; oss2 << "[";
1055 std::string oss2Str(oss2.str());
1056 bool isFinished=true;
1057 for(int i=0;i<nbOfTuples && isFinished;i++)
1062 for(int j=0;j<nbOfCompo;j++,data++)
1065 if(j!=nbOfCompo-1) oss2 << ", ";
1071 if(i!=nbOfTuples-1) oss2 << ", ";
1072 std::string oss3Str(oss2.str());
1073 if(oss3Str.length()<maxNbOfByteInRepr)
1085 * Equivalent to DataArrayDouble::isEqual except that if false the reason of
1086 * mismatch is given.
1088 * \param [in] other the instance to be compared with \a this
1089 * \param [in] prec the precision to compare numeric data of the arrays.
1090 * \param [out] reason In case of inequality returns the reason.
1091 * \sa DataArrayDouble::isEqual
1093 bool DataArrayDouble::isEqualIfNotWhy(const DataArrayDouble& other, double prec, std::string& reason) const
1095 if(!areInfoEqualsIfNotWhy(other,reason))
1097 return _mem.isEqual(other._mem,prec,reason);
1101 * Checks if \a this and another DataArrayDouble are fully equal. For more info see
1102 * \ref MEDCouplingArrayBasicsCompare.
1103 * \param [in] other - an instance of DataArrayDouble to compare with \a this one.
1104 * \param [in] prec - precision value to compare numeric data of the arrays.
1105 * \return bool - \a true if the two arrays are equal, \a false else.
1107 bool DataArrayDouble::isEqual(const DataArrayDouble& other, double prec) const
1110 return isEqualIfNotWhy(other,prec,tmp);
1114 * Checks if values of \a this and another DataArrayDouble are equal. For more info see
1115 * \ref MEDCouplingArrayBasicsCompare.
1116 * \param [in] other - an instance of DataArrayDouble to compare with \a this one.
1117 * \param [in] prec - precision value to compare numeric data of the arrays.
1118 * \return bool - \a true if the values of two arrays are equal, \a false else.
1120 bool DataArrayDouble::isEqualWithoutConsideringStr(const DataArrayDouble& other, double prec) const
1123 return _mem.isEqual(other._mem,prec,tmp);
1127 * This method checks that all tuples in \a other are in \a this.
1128 * If true, the output param \a tupleIds contains the tuples ids of \a this that correspond to tupes in \a this.
1129 * For each i in [ 0 , other->getNumberOfTuples() ) tuple #i in \a other is equal ( regarding input precision \a prec ) to tuple tupleIds[i] in \a this.
1131 * \param [in] other - the array having the same number of components than \a this.
1132 * \param [out] tupleIds - the tuple ids containing the same number of tuples than \a other has.
1133 * \sa DataArrayDouble::findCommonTuples
1135 bool DataArrayDouble::areIncludedInMe(const DataArrayDouble *other, double prec, DataArrayInt *&tupleIds) const
1138 throw INTERP_KERNEL::Exception("DataArrayDouble::areIncludedInMe : input array is NULL !");
1139 checkAllocated(); other->checkAllocated();
1140 if(getNumberOfComponents()!=other->getNumberOfComponents())
1141 throw INTERP_KERNEL::Exception("DataArrayDouble::areIncludedInMe : the number of components does not match !");
1142 MCAuto<DataArrayDouble> a=DataArrayDouble::Aggregate(this,other);
1143 DataArrayInt *c=0,*ci=0;
1144 a->findCommonTuples(prec,getNumberOfTuples(),c,ci);
1145 MCAuto<DataArrayInt> cSafe(c),ciSafe(ci);
1146 int newNbOfTuples=-1;
1147 MCAuto<DataArrayInt> ids=DataArrayInt::ConvertIndexArrayToO2N(a->getNumberOfTuples(),c->begin(),ci->begin(),ci->end(),newNbOfTuples);
1148 MCAuto<DataArrayInt> ret1=ids->selectByTupleIdSafeSlice(getNumberOfTuples(),a->getNumberOfTuples(),1);
1149 tupleIds=ret1.retn();
1150 return newNbOfTuples==getNumberOfTuples();
1154 * Searches for tuples coincident within \a prec tolerance. Each tuple is considered
1155 * as coordinates of a point in getNumberOfComponents()-dimensional space. The
1156 * distance separating two points is computed with the infinite norm.
1158 * Indices of coincident tuples are stored in output arrays.
1159 * A pair of arrays (\a comm, \a commIndex) is called "Surjective Format 2".
1161 * This method is typically used by MEDCouplingPointSet::findCommonNodes() and
1162 * MEDCouplingUMesh::mergeNodes().
1163 * \param [in] prec - minimal absolute distance between two tuples (infinite norm) at which they are
1164 * considered not coincident.
1165 * \param [in] limitTupleId - limit tuple id. If all tuples within a group of coincident
1166 * tuples have id strictly lower than \a limitTupleId then they are not returned.
1167 * \param [out] comm - the array holding ids (== indices) of coincident tuples.
1168 * \a comm->getNumberOfComponents() == 1.
1169 * \a comm->getNumberOfTuples() == \a commIndex->back().
1170 * \param [out] commIndex - the array dividing all indices stored in \a comm into
1171 * groups of (indices of) coincident tuples. Its every value is a tuple
1172 * index where a next group of tuples begins. For example the second
1173 * group of tuples in \a comm is described by following range of indices:
1174 * [ \a commIndex[1], \a commIndex[2] ). \a commIndex->getNumberOfTuples()-1
1175 * gives the number of groups of coincident tuples.
1176 * \throw If \a this is not allocated.
1177 * \throw If the number of components is not in [1,2,3,4].
1179 * \if ENABLE_EXAMPLES
1180 * \ref cpp_mcdataarraydouble_findcommontuples "Here is a C++ example".
1182 * \ref py_mcdataarraydouble_findcommontuples "Here is a Python example".
1184 * \sa DataArrayInt::ConvertIndexArrayToO2N(), DataArrayDouble::areIncludedInMe
1186 void DataArrayDouble::findCommonTuples(double prec, int limitTupleId, DataArrayInt *&comm, DataArrayInt *&commIndex) const
1189 int nbOfCompo=getNumberOfComponents();
1190 if ((nbOfCompo<1) || (nbOfCompo>4)) //test before work
1191 throw INTERP_KERNEL::Exception("DataArrayDouble::findCommonTuples : Unexpected spacedim of coords. Must be 1, 2, 3 or 4.");
1193 int nbOfTuples=getNumberOfTuples();
1195 MCAuto<DataArrayInt> c(DataArrayInt::New()),cI(DataArrayInt::New()); c->alloc(0,1); cI->pushBackSilent(0);
1199 findCommonTuplesAlg<4>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1202 findCommonTuplesAlg<3>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1205 findCommonTuplesAlg<2>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1208 findCommonTuplesAlg<1>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1211 throw INTERP_KERNEL::Exception("DataArrayDouble::findCommonTuples : nb of components managed are 1,2,3 and 4 ! not implemented for other number of components !");
1214 commIndex=cI.retn();
1218 * This methods returns the minimal distance between the two set of points \a this and \a other.
1219 * So \a this and \a other have to have the same number of components. If not an INTERP_KERNEL::Exception will be thrown.
1220 * This method works only if number of components of \a this (equal to those of \a other) is in 1, 2 or 3.
1222 * \param [out] thisTupleId the tuple id in \a this corresponding to the returned minimal distance
1223 * \param [out] otherTupleId the tuple id in \a other corresponding to the returned minimal distance
1224 * \return the minimal distance between the two set of points \a this and \a other.
1225 * \sa DataArrayDouble::findClosestTupleId
1227 double DataArrayDouble::minimalDistanceTo(const DataArrayDouble *other, int& thisTupleId, int& otherTupleId) const
1229 MCAuto<DataArrayInt> part1=findClosestTupleId(other);
1230 int nbOfCompo(getNumberOfComponents());
1231 int otherNbTuples(other->getNumberOfTuples());
1232 const double *thisPt(begin()),*otherPt(other->begin());
1233 const int *part1Pt(part1->begin());
1234 double ret=std::numeric_limits<double>::max();
1235 for(int i=0;i<otherNbTuples;i++,part1Pt++,otherPt+=nbOfCompo)
1238 for(int j=0;j<nbOfCompo;j++)
1239 tmp+=(otherPt[j]-thisPt[nbOfCompo*(*part1Pt)+j])*(otherPt[j]-thisPt[nbOfCompo*(*part1Pt)+j]);
1241 { ret=tmp; thisTupleId=*part1Pt; otherTupleId=i; }
1247 * This methods returns for each tuple in \a other which tuple in \a this is the closest.
1248 * So \a this and \a other have to have the same number of components. If not an INTERP_KERNEL::Exception will be thrown.
1249 * This method works only if number of components of \a this (equal to those of \a other) is in 1, 2 or 3.
1251 * \return a newly allocated (new object to be dealt by the caller) DataArrayInt having \c other->getNumberOfTuples() tuples and one components.
1252 * \sa DataArrayDouble::minimalDistanceTo
1254 DataArrayInt *DataArrayDouble::findClosestTupleId(const DataArrayDouble *other) const
1257 throw INTERP_KERNEL::Exception("DataArrayDouble::findClosestTupleId : other instance is NULL !");
1258 checkAllocated(); other->checkAllocated();
1259 int nbOfCompo=getNumberOfComponents();
1260 if(nbOfCompo!=other->getNumberOfComponents())
1262 std::ostringstream oss; oss << "DataArrayDouble::findClosestTupleId : number of components in this is " << nbOfCompo;
1263 oss << ", whereas number of components in other is " << other->getNumberOfComponents() << "! Should be equal !";
1264 throw INTERP_KERNEL::Exception(oss.str().c_str());
1266 int nbOfTuples=other->getNumberOfTuples();
1267 int thisNbOfTuples=getNumberOfTuples();
1268 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbOfTuples,1);
1270 getMinMaxPerComponent(bounds);
1275 double xDelta(fabs(bounds[1]-bounds[0])),yDelta(fabs(bounds[3]-bounds[2])),zDelta(fabs(bounds[5]-bounds[4]));
1276 double delta=std::max(xDelta,yDelta); delta=std::max(delta,zDelta);
1277 double characSize=pow((delta*delta*delta)/((double)thisNbOfTuples),1./3.);
1278 BBTreePts<3,int> myTree(begin(),0,0,getNumberOfTuples(),characSize*1e-12);
1279 FindClosestTupleIdAlg<3>(myTree,3.*characSize*characSize,other->begin(),nbOfTuples,begin(),thisNbOfTuples,ret->getPointer());
1284 double xDelta(fabs(bounds[1]-bounds[0])),yDelta(fabs(bounds[3]-bounds[2]));
1285 double delta=std::max(xDelta,yDelta);
1286 double characSize=sqrt(delta/(double)thisNbOfTuples);
1287 BBTreePts<2,int> myTree(begin(),0,0,getNumberOfTuples(),characSize*1e-12);
1288 FindClosestTupleIdAlg<2>(myTree,2.*characSize*characSize,other->begin(),nbOfTuples,begin(),thisNbOfTuples,ret->getPointer());
1293 double characSize=fabs(bounds[1]-bounds[0])/thisNbOfTuples;
1294 BBTreePts<1,int> myTree(begin(),0,0,getNumberOfTuples(),characSize*1e-12);
1295 FindClosestTupleIdAlg<1>(myTree,1.*characSize*characSize,other->begin(),nbOfTuples,begin(),thisNbOfTuples,ret->getPointer());
1299 throw INTERP_KERNEL::Exception("Unexpected spacedim of coords for findClosestTupleId. Must be 1, 2 or 3.");
1305 * This method expects that \a this and \a otherBBoxFrmt arrays are bounding box arrays ( as the output of MEDCouplingPointSet::getBoundingBoxForBBTree method ).
1306 * This method will return a DataArrayInt array having the same number of tuples than \a this. This returned array tells for each cell in \a this
1307 * how many bounding boxes in \a otherBBoxFrmt.
1308 * So, this method expects that \a this and \a otherBBoxFrmt have the same number of components.
1310 * \param [in] otherBBoxFrmt - It is an array .
1311 * \param [in] eps - the absolute precision of the detection. when eps < 0 the bboxes are enlarged so more interactions are detected. Inversely when > 0 the bboxes are stretched.
1312 * \sa MEDCouplingPointSet::getBoundingBoxForBBTree
1313 * \throw If \a this and \a otherBBoxFrmt have not the same number of components.
1314 * \throw If \a this and \a otherBBoxFrmt number of components is not even (BBox format).
1316 DataArrayInt *DataArrayDouble::computeNbOfInteractionsWith(const DataArrayDouble *otherBBoxFrmt, double eps) const
1319 throw INTERP_KERNEL::Exception("DataArrayDouble::computeNbOfInteractionsWith : input array is NULL !");
1320 if(!isAllocated() || !otherBBoxFrmt->isAllocated())
1321 throw INTERP_KERNEL::Exception("DataArrayDouble::computeNbOfInteractionsWith : this and input array must be allocated !");
1322 int nbOfComp(getNumberOfComponents()),nbOfTuples(getNumberOfTuples());
1323 if(nbOfComp!=otherBBoxFrmt->getNumberOfComponents())
1325 std::ostringstream oss; oss << "DataArrayDouble::computeNbOfInteractionsWith : this number of components (" << nbOfComp << ") must be equal to the number of components of input array (" << otherBBoxFrmt->getNumberOfComponents() << ") !";
1326 throw INTERP_KERNEL::Exception(oss.str().c_str());
1330 std::ostringstream oss; oss << "DataArrayDouble::computeNbOfInteractionsWith : Number of components (" << nbOfComp << ") is not even ! It should be to be compatible with bbox format !";
1331 throw INTERP_KERNEL::Exception(oss.str().c_str());
1333 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(nbOfTuples,1);
1334 const double *thisBBPtr(begin());
1335 int *retPtr(ret->getPointer());
1340 BBTree<3,int> bbt(otherBBoxFrmt->begin(),0,0,otherBBoxFrmt->getNumberOfTuples(),eps);
1341 for(int i=0;i<nbOfTuples;i++,retPtr++,thisBBPtr+=nbOfComp)
1342 *retPtr=bbt.getNbOfIntersectingElems(thisBBPtr);
1347 BBTree<2,int> bbt(otherBBoxFrmt->begin(),0,0,otherBBoxFrmt->getNumberOfTuples(),eps);
1348 for(int i=0;i<nbOfTuples;i++,retPtr++,thisBBPtr+=nbOfComp)
1349 *retPtr=bbt.getNbOfIntersectingElems(thisBBPtr);
1354 BBTree<1,int> bbt(otherBBoxFrmt->begin(),0,0,otherBBoxFrmt->getNumberOfTuples(),eps);
1355 for(int i=0;i<nbOfTuples;i++,retPtr++,thisBBPtr+=nbOfComp)
1356 *retPtr=bbt.getNbOfIntersectingElems(thisBBPtr);
1360 throw INTERP_KERNEL::Exception("DataArrayDouble::computeNbOfInteractionsWith : space dimension supported are [1,2,3] !");
1367 * Returns a copy of \a this array by excluding coincident tuples. Each tuple is
1368 * considered as coordinates of a point in getNumberOfComponents()-dimensional
1369 * space. The distance between tuples is computed using norm2. If several tuples are
1370 * not far each from other than \a prec, only one of them remains in the result
1371 * array. The order of tuples in the result array is same as in \a this one except
1372 * that coincident tuples are excluded.
1373 * \param [in] prec - minimal absolute distance between two tuples at which they are
1374 * considered not coincident.
1375 * \param [in] limitTupleId - limit tuple id. If all tuples within a group of coincident
1376 * tuples have id strictly lower than \a limitTupleId then they are not excluded.
1377 * \return DataArrayDouble * - the new instance of DataArrayDouble that the caller
1378 * is to delete using decrRef() as it is no more needed.
1379 * \throw If \a this is not allocated.
1380 * \throw If the number of components is not in [1,2,3,4].
1382 * \if ENABLE_EXAMPLES
1383 * \ref py_mcdataarraydouble_getdifferentvalues "Here is a Python example".
1386 DataArrayDouble *DataArrayDouble::getDifferentValues(double prec, int limitTupleId) const
1389 DataArrayInt *c0=0,*cI0=0;
1390 findCommonTuples(prec,limitTupleId,c0,cI0);
1391 MCAuto<DataArrayInt> c(c0),cI(cI0);
1392 int newNbOfTuples=-1;
1393 MCAuto<DataArrayInt> o2n=DataArrayInt::ConvertIndexArrayToO2N(getNumberOfTuples(),c0->begin(),cI0->begin(),cI0->end(),newNbOfTuples);
1394 return renumberAndReduce(o2n->getConstPointer(),newNbOfTuples);
1398 * Copy all components in a specified order from another DataArrayDouble.
1399 * Both numerical and textual data is copied. The number of tuples in \a this and
1400 * the other array can be different.
1401 * \param [in] a - the array to copy data from.
1402 * \param [in] compoIds - sequence of zero based indices of components, data of which is
1404 * \throw If \a a is NULL.
1405 * \throw If \a compoIds.size() != \a a->getNumberOfComponents().
1406 * \throw If \a compoIds[i] < 0 or \a compoIds[i] > \a this->getNumberOfComponents().
1408 * \if ENABLE_EXAMPLES
1409 * \ref py_mcdataarraydouble_setselectedcomponents "Here is a Python example".
1412 void DataArrayDouble::setSelectedComponents(const DataArrayDouble *a, const std::vector<int>& compoIds)
1415 throw INTERP_KERNEL::Exception("DataArrayDouble::setSelectedComponents : input DataArrayDouble is NULL !");
1417 copyPartOfStringInfoFrom2(compoIds,*a);
1418 std::size_t partOfCompoSz=compoIds.size();
1419 int nbOfCompo=getNumberOfComponents();
1420 int nbOfTuples=std::min(getNumberOfTuples(),a->getNumberOfTuples());
1421 const double *ac=a->getConstPointer();
1422 double *nc=getPointer();
1423 for(int i=0;i<nbOfTuples;i++)
1424 for(std::size_t j=0;j<partOfCompoSz;j++,ac++)
1425 nc[nbOfCompo*i+compoIds[j]]=*ac;
1429 * Checks if 0.0 value is present in \a this array. If it is the case, an exception
1431 * \throw If zero is found in \a this array.
1433 void DataArrayDouble::checkNoNullValues() const
1435 const double *tmp=getConstPointer();
1436 std::size_t nbOfElems=getNbOfElems();
1437 const double *where=std::find(tmp,tmp+nbOfElems,0.);
1438 if(where!=tmp+nbOfElems)
1439 throw INTERP_KERNEL::Exception("A value 0.0 have been detected !");
1443 * Computes minimal and maximal value in each component. An output array is filled
1444 * with \c 2 * \a this->getNumberOfComponents() values, so the caller is to allocate
1445 * enough memory before calling this method.
1446 * \param [out] bounds - array of size at least 2 *\a this->getNumberOfComponents().
1447 * It is filled as follows:<br>
1448 * \a bounds[0] = \c min_of_component_0 <br>
1449 * \a bounds[1] = \c max_of_component_0 <br>
1450 * \a bounds[2] = \c min_of_component_1 <br>
1451 * \a bounds[3] = \c max_of_component_1 <br>
1454 void DataArrayDouble::getMinMaxPerComponent(double *bounds) const
1457 int dim=getNumberOfComponents();
1458 for (int idim=0; idim<dim; idim++)
1460 bounds[idim*2]=std::numeric_limits<double>::max();
1461 bounds[idim*2+1]=-std::numeric_limits<double>::max();
1463 const double *ptr=getConstPointer();
1464 int nbOfTuples=getNumberOfTuples();
1465 for(int i=0;i<nbOfTuples;i++)
1467 for(int idim=0;idim<dim;idim++)
1469 if(bounds[idim*2]>ptr[i*dim+idim])
1471 bounds[idim*2]=ptr[i*dim+idim];
1473 if(bounds[idim*2+1]<ptr[i*dim+idim])
1475 bounds[idim*2+1]=ptr[i*dim+idim];
1482 * This method retrieves a newly allocated DataArrayDouble instance having same number of tuples than \a this and twice number of components than \a this
1483 * to store both the min and max per component of each tuples.
1484 * \param [in] epsilon the width of the bbox (identical in each direction) - 0.0 by default
1486 * \return a newly created DataArrayDouble instance having \c this->getNumberOfTuples() tuples and 2 * \c this->getNumberOfComponent() components
1488 * \throw If \a this is not allocated yet.
1490 DataArrayDouble *DataArrayDouble::computeBBoxPerTuple(double epsilon) const
1493 const double *dataPtr=getConstPointer();
1494 int nbOfCompo=getNumberOfComponents();
1495 int nbTuples=getNumberOfTuples();
1496 MCAuto<DataArrayDouble> bbox=DataArrayDouble::New();
1497 bbox->alloc(nbTuples,2*nbOfCompo);
1498 double *bboxPtr=bbox->getPointer();
1499 for(int i=0;i<nbTuples;i++)
1501 for(int j=0;j<nbOfCompo;j++)
1503 bboxPtr[2*nbOfCompo*i+2*j]=dataPtr[nbOfCompo*i+j]-epsilon;
1504 bboxPtr[2*nbOfCompo*i+2*j+1]=dataPtr[nbOfCompo*i+j]+epsilon;
1511 * For each tuples **t** in \a other, this method retrieves tuples in \a this that are equal to **t**.
1512 * Two tuples are considered equal if the euclidian distance between the two tuples is lower than \a eps.
1514 * \param [in] other a DataArrayDouble having same number of components than \a this.
1515 * \param [in] eps absolute precision representing distance (using infinite norm) between 2 tuples behind which 2 tuples are considered equal.
1516 * \param [out] c will contain the set of tuple ids in \a this that are equal to to the tuple ids in \a other contiguously.
1517 * \a cI allows to extract information in \a c.
1518 * \param [out] cI is an indirection array that allows to extract the data contained in \a c.
1520 * \throw In case of:
1521 * - \a this is not allocated
1522 * - \a other is not allocated or null
1523 * - \a this and \a other do not have the same number of components
1524 * - if number of components of \a this is not in [1,2,3]
1526 * \sa MEDCouplingPointSet::getNodeIdsNearPoints, DataArrayDouble::getDifferentValues
1528 void DataArrayDouble::computeTupleIdsNearTuples(const DataArrayDouble *other, double eps, DataArrayInt *& c, DataArrayInt *& cI) const
1531 throw INTERP_KERNEL::Exception("DataArrayDouble::computeTupleIdsNearTuples : input pointer other is null !");
1533 other->checkAllocated();
1534 int nbOfCompo=getNumberOfComponents();
1535 int otherNbOfCompo=other->getNumberOfComponents();
1536 if(nbOfCompo!=otherNbOfCompo)
1537 throw INTERP_KERNEL::Exception("DataArrayDouble::computeTupleIdsNearTuples : number of components should be equal between this and other !");
1538 int nbOfTuplesOther=other->getNumberOfTuples();
1539 MCAuto<DataArrayInt> cArr(DataArrayInt::New()),cIArr(DataArrayInt::New()); cArr->alloc(0,1); cIArr->pushBackSilent(0);
1544 BBTreePts<3,int> myTree(begin(),0,0,getNumberOfTuples(),eps);
1545 FindTupleIdsNearTuplesAlg<3>(myTree,other->getConstPointer(),nbOfTuplesOther,eps,cArr,cIArr);
1550 BBTreePts<2,int> myTree(begin(),0,0,getNumberOfTuples(),eps);
1551 FindTupleIdsNearTuplesAlg<2>(myTree,other->getConstPointer(),nbOfTuplesOther,eps,cArr,cIArr);
1556 BBTreePts<1,int> myTree(begin(),0,0,getNumberOfTuples(),eps);
1557 FindTupleIdsNearTuplesAlg<1>(myTree,other->getConstPointer(),nbOfTuplesOther,eps,cArr,cIArr);
1561 throw INTERP_KERNEL::Exception("Unexpected spacedim of coords for computeTupleIdsNearTuples. Must be 1, 2 or 3.");
1563 c=cArr.retn(); cI=cIArr.retn();
1567 * This method recenter tuples in \b this in order to be centered at the origin to benefit about the advantages of maximal precision to be around the box
1568 * around origin of 'radius' 1.
1570 * \param [in] eps absolute epsilon. under that value of delta between max and min no scale is performed.
1572 void DataArrayDouble::recenterForMaxPrecision(double eps)
1575 int dim=getNumberOfComponents();
1576 std::vector<double> bounds(2*dim);
1577 getMinMaxPerComponent(&bounds[0]);
1578 for(int i=0;i<dim;i++)
1580 double delta=bounds[2*i+1]-bounds[2*i];
1581 double offset=(bounds[2*i]+bounds[2*i+1])/2.;
1583 applyLin(1./delta,-offset/delta,i);
1585 applyLin(1.,-offset,i);
1590 * Returns the maximal value and all its locations within \a this one-dimensional array.
1591 * \param [out] tupleIds - a new instance of DataArrayInt containg indices of
1592 * tuples holding the maximal value. The caller is to delete it using
1593 * decrRef() as it is no more needed.
1594 * \return double - the maximal value among all values of \a this array.
1595 * \throw If \a this->getNumberOfComponents() != 1
1596 * \throw If \a this->getNumberOfTuples() < 1
1598 double DataArrayDouble::getMaxValue2(DataArrayInt*& tupleIds) const
1602 double ret=getMaxValue(tmp);
1603 tupleIds=findIdsInRange(ret,ret);
1608 * Returns the minimal value and all its locations within \a this one-dimensional array.
1609 * \param [out] tupleIds - a new instance of DataArrayInt containg indices of
1610 * tuples holding the minimal value. The caller is to delete it using
1611 * decrRef() as it is no more needed.
1612 * \return double - the minimal value among all values of \a this array.
1613 * \throw If \a this->getNumberOfComponents() != 1
1614 * \throw If \a this->getNumberOfTuples() < 1
1616 double DataArrayDouble::getMinValue2(DataArrayInt*& tupleIds) const
1620 double ret=getMinValue(tmp);
1621 tupleIds=findIdsInRange(ret,ret);
1626 * This method returns the number of values in \a this that are equals ( within an absolute precision of \a eps ) to input parameter \a value.
1627 * This method only works for single component array.
1629 * \return a value in [ 0, \c this->getNumberOfTuples() )
1631 * \throw If \a this is not allocated
1634 int DataArrayDouble::count(double value, double eps) const
1638 if(getNumberOfComponents()!=1)
1639 throw INTERP_KERNEL::Exception("DataArrayDouble::count : must be applied on DataArrayDouble with only one component, you can call 'rearrange' method before !");
1640 const double *vals=begin();
1641 int nbOfTuples=getNumberOfTuples();
1642 for(int i=0;i<nbOfTuples;i++,vals++)
1643 if(fabs(*vals-value)<=eps)
1649 * Returns the average value of \a this one-dimensional array.
1650 * \return double - the average value over all values of \a this array.
1651 * \throw If \a this->getNumberOfComponents() != 1
1652 * \throw If \a this->getNumberOfTuples() < 1
1654 double DataArrayDouble::getAverageValue() const
1656 if(getNumberOfComponents()!=1)
1657 throw INTERP_KERNEL::Exception("DataArrayDouble::getAverageValue : must be applied on DataArrayDouble with only one component, you can call 'rearrange' method before !");
1658 int nbOfTuples=getNumberOfTuples();
1660 throw INTERP_KERNEL::Exception("DataArrayDouble::getAverageValue : array exists but number of tuples must be > 0 !");
1661 const double *vals=getConstPointer();
1662 double ret=std::accumulate(vals,vals+nbOfTuples,0.);
1663 return ret/nbOfTuples;
1667 * Returns the Euclidean norm of the vector defined by \a this array.
1668 * \return double - the value of the Euclidean norm, i.e.
1669 * the square root of the inner product of vector.
1670 * \throw If \a this is not allocated.
1672 double DataArrayDouble::norm2() const
1676 std::size_t nbOfElems=getNbOfElems();
1677 const double *pt=getConstPointer();
1678 for(std::size_t i=0;i<nbOfElems;i++,pt++)
1684 * Returns the maximum norm of the vector defined by \a this array.
1685 * This method works even if the number of components is diferent from one.
1686 * If the number of elements in \a this is 0, -1. is returned.
1687 * \return double - the value of the maximum norm, i.e.
1688 * the maximal absolute value among values of \a this array (whatever its number of components).
1689 * \throw If \a this is not allocated.
1691 double DataArrayDouble::normMax() const
1695 std::size_t nbOfElems(getNbOfElems());
1696 const double *pt(getConstPointer());
1697 for(std::size_t i=0;i<nbOfElems;i++,pt++)
1699 double val(std::abs(*pt));
1707 * Returns the minimum norm (absolute value) of the vector defined by \a this array.
1708 * This method works even if the number of components is diferent from one.
1709 * If the number of elements in \a this is 0, std::numeric_limits<double>::max() is returned.
1710 * \return double - the value of the minimum norm, i.e.
1711 * the minimal absolute value among values of \a this array (whatever its number of components).
1712 * \throw If \a this is not allocated.
1714 double DataArrayDouble::normMin() const
1717 double ret(std::numeric_limits<double>::max());
1718 std::size_t nbOfElems(getNbOfElems());
1719 const double *pt(getConstPointer());
1720 for(std::size_t i=0;i<nbOfElems;i++,pt++)
1722 double val(std::abs(*pt));
1730 * Accumulates values of each component of \a this array.
1731 * \param [out] res - an array of length \a this->getNumberOfComponents(), allocated
1732 * by the caller, that is filled by this method with sum value for each
1734 * \throw If \a this is not allocated.
1736 void DataArrayDouble::accumulate(double *res) const
1739 const double *ptr=getConstPointer();
1740 int nbTuple=getNumberOfTuples();
1741 int nbComps=getNumberOfComponents();
1742 std::fill(res,res+nbComps,0.);
1743 for(int i=0;i<nbTuple;i++)
1744 std::transform(ptr+i*nbComps,ptr+(i+1)*nbComps,res,res,std::plus<double>());
1748 * This method returns the min distance from an external tuple defined by [ \a tupleBg , \a tupleEnd ) to \a this and
1749 * the first tuple in \a this that matches the returned distance. If there is no tuples in \a this an exception will be thrown.
1752 * \a this is expected to be allocated and expected to have a number of components equal to the distance from \a tupleBg to
1753 * \a tupleEnd. If not an exception will be thrown.
1755 * \param [in] tupleBg start pointer (included) of input external tuple
1756 * \param [in] tupleEnd end pointer (not included) of input external tuple
1757 * \param [out] tupleId the tuple id in \a this that matches the min of distance between \a this and input external tuple
1758 * \return the min distance.
1759 * \sa MEDCouplingUMesh::distanceToPoint
1761 double DataArrayDouble::distanceToTuple(const double *tupleBg, const double *tupleEnd, int& tupleId) const
1764 int nbTuple=getNumberOfTuples();
1765 int nbComps=getNumberOfComponents();
1766 if(nbComps!=(int)std::distance(tupleBg,tupleEnd))
1767 { std::ostringstream oss; oss << "DataArrayDouble::distanceToTuple : size of input tuple is " << std::distance(tupleBg,tupleEnd) << " should be equal to the number of components in this : " << nbComps << " !"; throw INTERP_KERNEL::Exception(oss.str().c_str()); }
1769 throw INTERP_KERNEL::Exception("DataArrayDouble::distanceToTuple : no tuple in this ! No distance to compute !");
1770 double ret0=std::numeric_limits<double>::max();
1772 const double *work=getConstPointer();
1773 for(int i=0;i<nbTuple;i++)
1776 for(int j=0;j<nbComps;j++,work++)
1777 val+=(*work-tupleBg[j])*((*work-tupleBg[j]));
1781 { ret0=val; tupleId=i; }
1787 * Accumulate values of the given component of \a this array.
1788 * \param [in] compId - the index of the component of interest.
1789 * \return double - a sum value of \a compId-th component.
1790 * \throw If \a this is not allocated.
1791 * \throw If \a the condition ( 0 <= \a compId < \a this->getNumberOfComponents() ) is
1794 double DataArrayDouble::accumulate(int compId) const
1797 const double *ptr=getConstPointer();
1798 int nbTuple=getNumberOfTuples();
1799 int nbComps=getNumberOfComponents();
1800 if(compId<0 || compId>=nbComps)
1801 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulate : Invalid compId specified : No such nb of components !");
1803 for(int i=0;i<nbTuple;i++)
1804 ret+=ptr[i*nbComps+compId];
1809 * This method accumulate using addition tuples in \a this using input index array [ \a bgOfIndex, \a endOfIndex ).
1810 * The returned array will have same number of components than \a this and number of tuples equal to
1811 * \c std::distance(bgOfIndex,endOfIndex) \b minus \b one.
1813 * The input index array is expected to be ascendingly sorted in which the all referenced ids should be in [0, \c this->getNumberOfTuples).
1814 * This method is quite useful for users that need to put a field on cells to field on nodes on the same mesh without a need of conservation.
1816 * \param [in] bgOfIndex - begin (included) of the input index array.
1817 * \param [in] endOfIndex - end (excluded) of the input index array.
1818 * \return DataArrayDouble * - the new instance having the same number of components than \a this.
1820 * \throw If bgOfIndex or end is NULL.
1821 * \throw If input index array is not ascendingly sorted.
1822 * \throw If there is an id in [ \a bgOfIndex, \a endOfIndex ) not in [0, \c this->getNumberOfTuples).
1823 * \throw If std::distance(bgOfIndex,endOfIndex)==0.
1825 DataArrayDouble *DataArrayDouble::accumulatePerChunck(const int *bgOfIndex, const int *endOfIndex) const
1827 if(!bgOfIndex || !endOfIndex)
1828 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulatePerChunck : input pointer NULL !");
1830 int nbCompo=getNumberOfComponents();
1831 int nbOfTuples=getNumberOfTuples();
1832 int sz=(int)std::distance(bgOfIndex,endOfIndex);
1834 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulatePerChunck : invalid size of input index array !");
1836 MCAuto<DataArrayDouble> ret=DataArrayDouble::New(); ret->alloc(sz,nbCompo);
1837 const int *w=bgOfIndex;
1838 if(*w<0 || *w>=nbOfTuples)
1839 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulatePerChunck : The first element of the input index not in [0,nbOfTuples) !");
1840 const double *srcPt=begin()+(*w)*nbCompo;
1841 double *tmp=ret->getPointer();
1842 for(int i=0;i<sz;i++,tmp+=nbCompo,w++)
1844 std::fill(tmp,tmp+nbCompo,0.);
1847 for(int j=w[0];j<w[1];j++,srcPt+=nbCompo)
1849 if(j>=0 && j<nbOfTuples)
1850 std::transform(srcPt,srcPt+nbCompo,tmp,tmp,std::plus<double>());
1853 std::ostringstream oss; oss << "DataArrayDouble::accumulatePerChunck : At rank #" << i << " the input index array points to id " << j << " should be in [0," << nbOfTuples << ") !";
1854 throw INTERP_KERNEL::Exception(oss.str().c_str());
1860 std::ostringstream oss; oss << "DataArrayDouble::accumulatePerChunck : At rank #" << i << " the input index array is not in ascendingly sorted.";
1861 throw INTERP_KERNEL::Exception(oss.str().c_str());
1864 ret->copyStringInfoFrom(*this);
1869 * This method is close to numpy cumSum except that number of element is equal to \a this->getNumberOfTuples()+1. First element of DataArray returned is equal to 0.
1870 * This method expects that \a this as only one component. The returned array will have \a this->getNumberOfTuples()+1 tuple with also one component.
1871 * The ith element of returned array is equal to the sum of elements in \a this with rank strictly lower than i.
1873 * \return DataArrayDouble - A newly built array containing cum sum of \a this.
1875 MCAuto<DataArrayDouble> DataArrayDouble::cumSum() const
1878 checkNbOfComps(1,"DataArrayDouble::cumSum : this is expected to be single component");
1879 int nbOfTuple(getNumberOfTuples());
1880 MCAuto<DataArrayDouble> ret(DataArrayDouble::New()); ret->alloc(nbOfTuple+1,1);
1881 double *ptr(ret->getPointer());
1883 const double *thisPtr(begin());
1884 for(int i=0;i<nbOfTuple;i++)
1885 ptr[i+1]=ptr[i]+thisPtr[i];
1890 * Converts each 2D point defined by the tuple of \a this array from the Polar to the
1891 * Cartesian coordinate system. The two components of the tuple of \a this array are
1892 * considered to contain (1) radius and (2) angle of the point in the Polar CS.
1893 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
1894 * contains X and Y coordinates of the point in the Cartesian CS. The caller
1895 * is to delete this array using decrRef() as it is no more needed. The array
1896 * does not contain any textual info on components.
1897 * \throw If \a this->getNumberOfComponents() != 2.
1898 * \sa fromCartToPolar
1900 DataArrayDouble *DataArrayDouble::fromPolarToCart() const
1903 int nbOfComp(getNumberOfComponents());
1905 throw INTERP_KERNEL::Exception("DataArrayDouble::fromPolarToCart : must be an array with exactly 2 components !");
1906 int nbOfTuple(getNumberOfTuples());
1907 DataArrayDouble *ret(DataArrayDouble::New());
1908 ret->alloc(nbOfTuple,2);
1909 double *w(ret->getPointer());
1910 const double *wIn(getConstPointer());
1911 for(int i=0;i<nbOfTuple;i++,w+=2,wIn+=2)
1913 w[0]=wIn[0]*cos(wIn[1]);
1914 w[1]=wIn[0]*sin(wIn[1]);
1920 * Converts each 3D point defined by the tuple of \a this array from the Cylindrical to
1921 * the Cartesian coordinate system. The three components of the tuple of \a this array
1922 * are considered to contain (1) radius, (2) azimuth and (3) altitude of the point in
1923 * the Cylindrical CS.
1924 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
1925 * contains X, Y and Z coordinates of the point in the Cartesian CS. The info
1926 * on the third component is copied from \a this array. The caller
1927 * is to delete this array using decrRef() as it is no more needed.
1928 * \throw If \a this->getNumberOfComponents() != 3.
1931 DataArrayDouble *DataArrayDouble::fromCylToCart() const
1934 int nbOfComp(getNumberOfComponents());
1936 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCylToCart : must be an array with exactly 3 components !");
1937 int nbOfTuple(getNumberOfTuples());
1938 DataArrayDouble *ret(DataArrayDouble::New());
1939 ret->alloc(getNumberOfTuples(),3);
1940 double *w(ret->getPointer());
1941 const double *wIn(getConstPointer());
1942 for(int i=0;i<nbOfTuple;i++,w+=3,wIn+=3)
1944 w[0]=wIn[0]*cos(wIn[1]);
1945 w[1]=wIn[0]*sin(wIn[1]);
1948 ret->setInfoOnComponent(2,getInfoOnComponent(2));
1953 * Converts each 3D point defined by the tuple of \a this array from the Spherical to
1954 * the Cartesian coordinate system. The three components of the tuple of \a this array
1955 * are considered to contain (1) radius, (2) polar angle and (3) azimuthal angle of the
1956 * point in the Cylindrical CS.
1957 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
1958 * contains X, Y and Z coordinates of the point in the Cartesian CS. The info
1959 * on the third component is copied from \a this array. The caller
1960 * is to delete this array using decrRef() as it is no more needed.
1961 * \throw If \a this->getNumberOfComponents() != 3.
1962 * \sa fromCartToSpher
1964 DataArrayDouble *DataArrayDouble::fromSpherToCart() const
1967 int nbOfComp(getNumberOfComponents());
1969 throw INTERP_KERNEL::Exception("DataArrayDouble::fromSpherToCart : must be an array with exactly 3 components !");
1970 int nbOfTuple(getNumberOfTuples());
1971 DataArrayDouble *ret(DataArrayDouble::New());
1972 ret->alloc(getNumberOfTuples(),3);
1973 double *w(ret->getPointer());
1974 const double *wIn(getConstPointer());
1975 for(int i=0;i<nbOfTuple;i++,w+=3,wIn+=3)
1977 w[0]=wIn[0]*cos(wIn[2])*sin(wIn[1]);
1978 w[1]=wIn[0]*sin(wIn[2])*sin(wIn[1]);
1979 w[2]=wIn[0]*cos(wIn[1]);
1985 * This method returns a new array containing the same number of tuples than \a this. To do this, this method needs \a at parameter to specify the convention of \a this.
1986 * All the tuples of the returned array will be in cartesian sense. So if \a at equals to AX_CART the returned array is basically a deep copy of \a this.
1987 * If \a at equals to AX_CYL the returned array will be the result of operation cylindric to cartesian of \a this...
1989 * \param [in] atOfThis - The axis type of \a this.
1990 * \return DataArrayDouble * - the new instance of DataArrayDouble (that must be dealed by caller) containing the result of the cartesianizification of \a this.
1992 DataArrayDouble *DataArrayDouble::cartesianize(MEDCouplingAxisType atOfThis) const
1995 int nbOfComp(getNumberOfComponents());
1996 MCAuto<DataArrayDouble> ret;
2004 ret=fromCylToCart();
2009 ret=fromPolarToCart();
2013 throw INTERP_KERNEL::Exception("DataArrayDouble::cartesianize : For AX_CYL, number of components must be in [2,3] !");
2017 ret=fromSpherToCart();
2022 ret=fromPolarToCart();
2026 throw INTERP_KERNEL::Exception("DataArrayDouble::cartesianize : For AX_CYL, number of components must be in [2,3] !");
2028 throw INTERP_KERNEL::Exception("DataArrayDouble::cartesianize : not recognized axis type ! Only AX_CART, AX_CYL and AX_SPHER supported !");
2030 ret->copyStringInfoFrom(*this);
2035 * This method returns a newly created array to be deallocated that contains the result of conversion from cartesian to polar.
2036 * This method expects that \a this has exactly 2 components.
2037 * \sa fromPolarToCart
2039 DataArrayDouble *DataArrayDouble::fromCartToPolar() const
2041 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2043 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2045 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToPolar : must be an array with exactly 2 components !");
2046 ret->alloc(nbTuples,2);
2047 double *retPtr(ret->getPointer());
2048 const double *ptr(begin());
2049 for(int i=0;i<nbTuples;i++,ptr+=2,retPtr+=2)
2051 retPtr[0]=sqrt(ptr[0]*ptr[0]+ptr[1]*ptr[1]);
2052 retPtr[1]=atan2(ptr[1],ptr[0]);
2058 * This method returns a newly created array to be deallocated that contains the result of conversion from cartesian to cylindrical.
2059 * This method expects that \a this has exactly 3 components.
2062 DataArrayDouble *DataArrayDouble::fromCartToCyl() const
2064 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2066 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2068 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCyl : must be an array with exactly 3 components !");
2069 ret->alloc(nbTuples,3);
2070 double *retPtr(ret->getPointer());
2071 const double *ptr(begin());
2072 for(int i=0;i<nbTuples;i++,ptr+=3,retPtr+=3)
2074 retPtr[0]=sqrt(ptr[0]*ptr[0]+ptr[1]*ptr[1]);
2075 retPtr[1]=atan2(ptr[1],ptr[0]);
2082 * This method returns a newly created array to be deallocated that contains the result of conversion from cartesian to spherical coordinates.
2083 * \sa fromSpherToCart
2085 DataArrayDouble *DataArrayDouble::fromCartToSpher() const
2087 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2089 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2091 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToSpher : must be an array with exactly 3 components !");
2092 ret->alloc(nbTuples,3);
2093 double *retPtr(ret->getPointer());
2094 const double *ptr(begin());
2095 for(int i=0;i<nbTuples;i++,ptr+=3,retPtr+=3)
2097 retPtr[0]=sqrt(ptr[0]*ptr[0]+ptr[1]*ptr[1]+ptr[2]*ptr[2]);
2098 retPtr[1]=acos(ptr[2]/retPtr[0]);
2099 retPtr[2]=atan2(ptr[1],ptr[0]);
2105 * This method returns a newly created array to be deallocated that contains the result of conversion from cartesian to cylindrical relative to the given \a center and a \a vector.
2106 * This method expects that \a this has exactly 3 components.
2107 * \sa MEDCouplingFieldDouble::computeVectorFieldCyl
2109 DataArrayDouble *DataArrayDouble::fromCartToCylGiven(const DataArrayDouble *coords, const double center[3], const double vect[3]) const
2112 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : input coords are NULL !");
2113 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2114 checkAllocated(); coords->checkAllocated();
2115 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2117 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : must be an array with exactly 3 components !");
2118 if(coords->getNumberOfComponents()!=3)
2119 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : coords array must have exactly 3 components !");
2120 if(coords->getNumberOfTuples()!=nbTuples)
2121 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : coords array must have the same number of tuples !");
2122 ret->alloc(nbTuples,nbOfComp);
2123 double magOfVect(sqrt(vect[0]*vect[0]+vect[1]*vect[1]+vect[2]*vect[2]));
2125 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : magnitude of vect is too low !");
2126 double Ur[3],Uteta[3],Uz[3],*retPtr(ret->getPointer());
2127 const double *coo(coords->begin()),*vectField(begin());
2128 std::transform(vect,vect+3,Uz,std::bind2nd(std::multiplies<double>(),1./magOfVect));
2129 for(int i=0;i<nbTuples;i++,vectField+=3,retPtr+=3,coo+=3)
2131 std::transform(coo,coo+3,center,Ur,std::minus<double>());
2132 Uteta[0]=Uz[1]*Ur[2]-Uz[2]*Ur[1]; Uteta[1]=Uz[2]*Ur[0]-Uz[0]*Ur[2]; Uteta[2]=Uz[0]*Ur[1]-Uz[1]*Ur[0];
2133 double magOfTeta(sqrt(Uteta[0]*Uteta[0]+Uteta[1]*Uteta[1]+Uteta[2]*Uteta[2]));
2134 std::transform(Uteta,Uteta+3,Uteta,std::bind2nd(std::multiplies<double>(),1./magOfTeta));
2135 Ur[0]=Uteta[1]*Uz[2]-Uteta[2]*Uz[1]; Ur[1]=Uteta[2]*Uz[0]-Uteta[0]*Uz[2]; Ur[2]=Uteta[0]*Uz[1]-Uteta[1]*Uz[0];
2136 retPtr[0]=Ur[0]*vectField[0]+Ur[1]*vectField[1]+Ur[2]*vectField[2];
2137 retPtr[1]=Uteta[0]*vectField[0]+Uteta[1]*vectField[1]+Uteta[2]*vectField[2];
2138 retPtr[2]=Uz[0]*vectField[0]+Uz[1]*vectField[1]+Uz[2]*vectField[2];
2140 ret->copyStringInfoFrom(*this);
2145 * Computes the doubly contracted product of every tensor defined by the tuple of \a this
2146 * array contating 6 components.
2147 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
2148 * is calculated from the tuple <em>(t)</em> of \a this array as follows:
2149 * \f$ t[0]^2+t[1]^2+t[2]^2+2*t[3]^2+2*t[4]^2+2*t[5]^2\f$.
2150 * The caller is to delete this result array using decrRef() as it is no more needed.
2151 * \throw If \a this->getNumberOfComponents() != 6.
2153 DataArrayDouble *DataArrayDouble::doublyContractedProduct() const
2156 int nbOfComp(getNumberOfComponents());
2158 throw INTERP_KERNEL::Exception("DataArrayDouble::doublyContractedProduct : must be an array with exactly 6 components !");
2159 DataArrayDouble *ret=DataArrayDouble::New();
2160 int nbOfTuple=getNumberOfTuples();
2161 ret->alloc(nbOfTuple,1);
2162 const double *src=getConstPointer();
2163 double *dest=ret->getPointer();
2164 for(int i=0;i<nbOfTuple;i++,dest++,src+=6)
2165 *dest=src[0]*src[0]+src[1]*src[1]+src[2]*src[2]+2.*src[3]*src[3]+2.*src[4]*src[4]+2.*src[5]*src[5];
2170 * Computes the determinant of every square matrix defined by the tuple of \a this
2171 * array, which contains either 4, 6 or 9 components. The case of 6 components
2172 * corresponds to that of the upper triangular matrix.
2173 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
2174 * is the determinant of matrix of the corresponding tuple of \a this array.
2175 * The caller is to delete this result array using decrRef() as it is no more
2177 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2179 DataArrayDouble *DataArrayDouble::determinant() const
2182 DataArrayDouble *ret=DataArrayDouble::New();
2183 int nbOfTuple=getNumberOfTuples();
2184 ret->alloc(nbOfTuple,1);
2185 const double *src=getConstPointer();
2186 double *dest=ret->getPointer();
2187 switch(getNumberOfComponents())
2190 for(int i=0;i<nbOfTuple;i++,dest++,src+=6)
2191 *dest=src[0]*src[1]*src[2]+2.*src[4]*src[5]*src[3]-src[0]*src[4]*src[4]-src[2]*src[3]*src[3]-src[1]*src[5]*src[5];
2194 for(int i=0;i<nbOfTuple;i++,dest++,src+=4)
2195 *dest=src[0]*src[3]-src[1]*src[2];
2198 for(int i=0;i<nbOfTuple;i++,dest++,src+=9)
2199 *dest=src[0]*src[4]*src[8]+src[1]*src[5]*src[6]+src[2]*src[3]*src[7]-src[0]*src[5]*src[7]-src[1]*src[3]*src[8]-src[2]*src[4]*src[6];
2203 throw INTERP_KERNEL::Exception("DataArrayDouble::determinant : Invalid number of components ! must be in 4,6,9 !");
2208 * Computes 3 eigenvalues of every upper triangular matrix defined by the tuple of
2209 * \a this array, which contains 6 components.
2210 * \return DataArrayDouble * - the new instance of DataArrayDouble containing 3
2211 * components, whose each tuple contains the eigenvalues of the matrix of
2212 * corresponding tuple of \a this array.
2213 * The caller is to delete this result array using decrRef() as it is no more
2215 * \throw If \a this->getNumberOfComponents() != 6.
2217 DataArrayDouble *DataArrayDouble::eigenValues() const
2220 int nbOfComp=getNumberOfComponents();
2222 throw INTERP_KERNEL::Exception("DataArrayDouble::eigenValues : must be an array with exactly 6 components !");
2223 DataArrayDouble *ret=DataArrayDouble::New();
2224 int nbOfTuple=getNumberOfTuples();
2225 ret->alloc(nbOfTuple,3);
2226 const double *src=getConstPointer();
2227 double *dest=ret->getPointer();
2228 for(int i=0;i<nbOfTuple;i++,dest+=3,src+=6)
2229 INTERP_KERNEL::computeEigenValues6(src,dest);
2234 * Computes 3 eigenvectors of every upper triangular matrix defined by the tuple of
2235 * \a this array, which contains 6 components.
2236 * \return DataArrayDouble * - the new instance of DataArrayDouble containing 9
2237 * components, whose each tuple contains 3 eigenvectors of the matrix of
2238 * corresponding tuple of \a this array.
2239 * The caller is to delete this result array using decrRef() as it is no more
2241 * \throw If \a this->getNumberOfComponents() != 6.
2243 DataArrayDouble *DataArrayDouble::eigenVectors() const
2246 int nbOfComp=getNumberOfComponents();
2248 throw INTERP_KERNEL::Exception("DataArrayDouble::eigenVectors : must be an array with exactly 6 components !");
2249 DataArrayDouble *ret=DataArrayDouble::New();
2250 int nbOfTuple=getNumberOfTuples();
2251 ret->alloc(nbOfTuple,9);
2252 const double *src=getConstPointer();
2253 double *dest=ret->getPointer();
2254 for(int i=0;i<nbOfTuple;i++,src+=6)
2257 INTERP_KERNEL::computeEigenValues6(src,tmp);
2258 for(int j=0;j<3;j++,dest+=3)
2259 INTERP_KERNEL::computeEigenVectorForEigenValue6(src,tmp[j],1e-12,dest);
2265 * Computes the inverse matrix of every matrix defined by the tuple of \a this
2266 * array, which contains either 4, 6 or 9 components. The case of 6 components
2267 * corresponds to that of the upper triangular matrix.
2268 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2269 * same number of components as \a this one, whose each tuple is the inverse
2270 * matrix of the matrix of corresponding tuple of \a this array.
2271 * The caller is to delete this result array using decrRef() as it is no more
2273 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2275 DataArrayDouble *DataArrayDouble::inverse() const
2278 int nbOfComp=getNumberOfComponents();
2279 if(nbOfComp!=6 && nbOfComp!=9 && nbOfComp!=4)
2280 throw INTERP_KERNEL::Exception("DataArrayDouble::inversion : must be an array with 4,6 or 9 components !");
2281 DataArrayDouble *ret=DataArrayDouble::New();
2282 int nbOfTuple=getNumberOfTuples();
2283 ret->alloc(nbOfTuple,nbOfComp);
2284 const double *src=getConstPointer();
2285 double *dest=ret->getPointer();
2287 for(int i=0;i<nbOfTuple;i++,dest+=6,src+=6)
2289 double det=src[0]*src[1]*src[2]+2.*src[4]*src[5]*src[3]-src[0]*src[4]*src[4]-src[2]*src[3]*src[3]-src[1]*src[5]*src[5];
2290 dest[0]=(src[1]*src[2]-src[4]*src[4])/det;
2291 dest[1]=(src[0]*src[2]-src[5]*src[5])/det;
2292 dest[2]=(src[0]*src[1]-src[3]*src[3])/det;
2293 dest[3]=(src[5]*src[4]-src[3]*src[2])/det;
2294 dest[4]=(src[5]*src[3]-src[0]*src[4])/det;
2295 dest[5]=(src[3]*src[4]-src[1]*src[5])/det;
2297 else if(nbOfComp==4)
2298 for(int i=0;i<nbOfTuple;i++,dest+=4,src+=4)
2300 double det=src[0]*src[3]-src[1]*src[2];
2302 dest[1]=-src[1]/det;
2303 dest[2]=-src[2]/det;
2307 for(int i=0;i<nbOfTuple;i++,dest+=9,src+=9)
2309 double det=src[0]*src[4]*src[8]+src[1]*src[5]*src[6]+src[2]*src[3]*src[7]-src[0]*src[5]*src[7]-src[1]*src[3]*src[8]-src[2]*src[4]*src[6];
2310 dest[0]=(src[4]*src[8]-src[7]*src[5])/det;
2311 dest[1]=(src[7]*src[2]-src[1]*src[8])/det;
2312 dest[2]=(src[1]*src[5]-src[4]*src[2])/det;
2313 dest[3]=(src[6]*src[5]-src[3]*src[8])/det;
2314 dest[4]=(src[0]*src[8]-src[6]*src[2])/det;
2315 dest[5]=(src[2]*src[3]-src[0]*src[5])/det;
2316 dest[6]=(src[3]*src[7]-src[6]*src[4])/det;
2317 dest[7]=(src[6]*src[1]-src[0]*src[7])/det;
2318 dest[8]=(src[0]*src[4]-src[1]*src[3])/det;
2324 * Computes the trace of every matrix defined by the tuple of \a this
2325 * array, which contains either 4, 6 or 9 components. The case of 6 components
2326 * corresponds to that of the upper triangular matrix.
2327 * \return DataArrayDouble * - the new instance of DataArrayDouble containing
2328 * 1 component, whose each tuple is the trace of
2329 * the matrix of corresponding tuple of \a this array.
2330 * The caller is to delete this result array using decrRef() as it is no more
2332 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2334 DataArrayDouble *DataArrayDouble::trace() const
2337 int nbOfComp=getNumberOfComponents();
2338 if(nbOfComp!=6 && nbOfComp!=9 && nbOfComp!=4)
2339 throw INTERP_KERNEL::Exception("DataArrayDouble::trace : must be an array with 4,6 or 9 components !");
2340 DataArrayDouble *ret=DataArrayDouble::New();
2341 int nbOfTuple=getNumberOfTuples();
2342 ret->alloc(nbOfTuple,1);
2343 const double *src=getConstPointer();
2344 double *dest=ret->getPointer();
2346 for(int i=0;i<nbOfTuple;i++,dest++,src+=6)
2347 *dest=src[0]+src[1]+src[2];
2348 else if(nbOfComp==4)
2349 for(int i=0;i<nbOfTuple;i++,dest++,src+=4)
2350 *dest=src[0]+src[3];
2352 for(int i=0;i<nbOfTuple;i++,dest++,src+=9)
2353 *dest=src[0]+src[4]+src[8];
2358 * Computes the stress deviator tensor of every stress tensor defined by the tuple of
2359 * \a this array, which contains 6 components.
2360 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2361 * same number of components and tuples as \a this array.
2362 * The caller is to delete this result array using decrRef() as it is no more
2364 * \throw If \a this->getNumberOfComponents() != 6.
2366 DataArrayDouble *DataArrayDouble::deviator() const
2369 int nbOfComp=getNumberOfComponents();
2371 throw INTERP_KERNEL::Exception("DataArrayDouble::deviator : must be an array with exactly 6 components !");
2372 DataArrayDouble *ret=DataArrayDouble::New();
2373 int nbOfTuple=getNumberOfTuples();
2374 ret->alloc(nbOfTuple,6);
2375 const double *src=getConstPointer();
2376 double *dest=ret->getPointer();
2377 for(int i=0;i<nbOfTuple;i++,dest+=6,src+=6)
2379 double tr=(src[0]+src[1]+src[2])/3.;
2391 * Computes the magnitude of every vector defined by the tuple of
2393 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2394 * same number of tuples as \a this array and one component.
2395 * The caller is to delete this result array using decrRef() as it is no more
2397 * \throw If \a this is not allocated.
2399 DataArrayDouble *DataArrayDouble::magnitude() const
2402 int nbOfComp=getNumberOfComponents();
2403 DataArrayDouble *ret=DataArrayDouble::New();
2404 int nbOfTuple=getNumberOfTuples();
2405 ret->alloc(nbOfTuple,1);
2406 const double *src=getConstPointer();
2407 double *dest=ret->getPointer();
2408 for(int i=0;i<nbOfTuple;i++,dest++)
2411 for(int j=0;j<nbOfComp;j++,src++)
2419 * Computes for each tuple the sum of number of components values in the tuple and return it.
2421 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2422 * same number of tuples as \a this array and one component.
2423 * The caller is to delete this result array using decrRef() as it is no more
2425 * \throw If \a this is not allocated.
2427 DataArrayDouble *DataArrayDouble::sumPerTuple() const
2430 int nbOfComp(getNumberOfComponents()),nbOfTuple(getNumberOfTuples());
2431 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2432 ret->alloc(nbOfTuple,1);
2433 const double *src(getConstPointer());
2434 double *dest(ret->getPointer());
2435 for(int i=0;i<nbOfTuple;i++,dest++,src+=nbOfComp)
2436 *dest=std::accumulate(src,src+nbOfComp,0.);
2441 * Computes the maximal value within every tuple of \a this array.
2442 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2443 * same number of tuples as \a this array and one component.
2444 * The caller is to delete this result array using decrRef() as it is no more
2446 * \throw If \a this is not allocated.
2447 * \sa DataArrayDouble::maxPerTupleWithCompoId
2449 DataArrayDouble *DataArrayDouble::maxPerTuple() const
2452 int nbOfComp=getNumberOfComponents();
2453 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
2454 int nbOfTuple=getNumberOfTuples();
2455 ret->alloc(nbOfTuple,1);
2456 const double *src=getConstPointer();
2457 double *dest=ret->getPointer();
2458 for(int i=0;i<nbOfTuple;i++,dest++,src+=nbOfComp)
2459 *dest=*std::max_element(src,src+nbOfComp);
2464 * Computes the maximal value within every tuple of \a this array and it returns the first component
2465 * id for each tuple that corresponds to the maximal value within the tuple.
2467 * \param [out] compoIdOfMaxPerTuple - the new new instance of DataArrayInt containing the
2468 * same number of tuples and only one component.
2469 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2470 * same number of tuples as \a this array and one component.
2471 * The caller is to delete this result array using decrRef() as it is no more
2473 * \throw If \a this is not allocated.
2474 * \sa DataArrayDouble::maxPerTuple
2476 DataArrayDouble *DataArrayDouble::maxPerTupleWithCompoId(DataArrayInt* &compoIdOfMaxPerTuple) const
2479 int nbOfComp=getNumberOfComponents();
2480 MCAuto<DataArrayDouble> ret0=DataArrayDouble::New();
2481 MCAuto<DataArrayInt> ret1=DataArrayInt::New();
2482 int nbOfTuple=getNumberOfTuples();
2483 ret0->alloc(nbOfTuple,1); ret1->alloc(nbOfTuple,1);
2484 const double *src=getConstPointer();
2485 double *dest=ret0->getPointer(); int *dest1=ret1->getPointer();
2486 for(int i=0;i<nbOfTuple;i++,dest++,dest1++,src+=nbOfComp)
2488 const double *loc=std::max_element(src,src+nbOfComp);
2490 *dest1=(int)std::distance(src,loc);
2492 compoIdOfMaxPerTuple=ret1.retn();
2497 * This method returns a newly allocated DataArrayDouble instance having one component and \c this->getNumberOfTuples() * \c this->getNumberOfTuples() tuples.
2498 * \n This returned array contains the euclidian distance for each tuple in \a this.
2499 * \n So the returned array can be seen as a dense symmetrical matrix whose diagonal elements are equal to 0.
2500 * \n The returned array has only one component (and **not** \c this->getNumberOfTuples() components to avoid the useless memory consumption due to components info in returned DataArrayDouble)
2502 * \warning use this method with care because it can leads to big amount of consumed memory !
2504 * \return A newly allocated (huge) MEDCoupling::DataArrayDouble instance that the caller should deal with.
2506 * \throw If \a this is not allocated.
2508 * \sa DataArrayDouble::buildEuclidianDistanceDenseMatrixWith
2510 DataArrayDouble *DataArrayDouble::buildEuclidianDistanceDenseMatrix() const
2513 int nbOfComp=getNumberOfComponents();
2514 int nbOfTuples=getNumberOfTuples();
2515 const double *inData=getConstPointer();
2516 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
2517 ret->alloc(nbOfTuples*nbOfTuples,1);
2518 double *outData=ret->getPointer();
2519 for(int i=0;i<nbOfTuples;i++)
2521 outData[i*nbOfTuples+i]=0.;
2522 for(int j=i+1;j<nbOfTuples;j++)
2525 for(int k=0;k<nbOfComp;k++)
2526 { double delta=inData[i*nbOfComp+k]-inData[j*nbOfComp+k]; dist+=delta*delta; }
2528 outData[i*nbOfTuples+j]=dist;
2529 outData[j*nbOfTuples+i]=dist;
2536 * This method returns a newly allocated DataArrayDouble instance having one component and \c this->getNumberOfTuples() * \c other->getNumberOfTuples() tuples.
2537 * \n This returned array contains the euclidian distance for each tuple in \a other with each tuple in \a this.
2538 * \n So the returned array can be seen as a dense rectangular matrix with \c other->getNumberOfTuples() rows and \c this->getNumberOfTuples() columns.
2539 * \n Output rectangular matrix is sorted along rows.
2540 * \n The returned array has only one component (and **not** \c this->getNumberOfTuples() components to avoid the useless memory consumption due to components info in returned DataArrayDouble)
2542 * \warning use this method with care because it can leads to big amount of consumed memory !
2544 * \param [in] other DataArrayDouble instance having same number of components than \a this.
2545 * \return A newly allocated (huge) MEDCoupling::DataArrayDouble instance that the caller should deal with.
2547 * \throw If \a this is not allocated, or if \a other is null or if \a other is not allocated, or if number of components of \a other and \a this differs.
2549 * \sa DataArrayDouble::buildEuclidianDistanceDenseMatrix
2551 DataArrayDouble *DataArrayDouble::buildEuclidianDistanceDenseMatrixWith(const DataArrayDouble *other) const
2554 throw INTERP_KERNEL::Exception("DataArrayDouble::buildEuclidianDistanceDenseMatrixWith : input parameter is null !");
2556 other->checkAllocated();
2557 int nbOfComp=getNumberOfComponents();
2558 int otherNbOfComp=other->getNumberOfComponents();
2559 if(nbOfComp!=otherNbOfComp)
2561 std::ostringstream oss; oss << "DataArrayDouble::buildEuclidianDistanceDenseMatrixWith : this nb of compo=" << nbOfComp << " and other nb of compo=" << otherNbOfComp << ". It should match !";
2562 throw INTERP_KERNEL::Exception(oss.str().c_str());
2564 int nbOfTuples=getNumberOfTuples();
2565 int otherNbOfTuples=other->getNumberOfTuples();
2566 const double *inData=getConstPointer();
2567 const double *inDataOther=other->getConstPointer();
2568 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
2569 ret->alloc(otherNbOfTuples*nbOfTuples,1);
2570 double *outData=ret->getPointer();
2571 for(int i=0;i<otherNbOfTuples;i++,inDataOther+=nbOfComp)
2573 for(int j=0;j<nbOfTuples;j++)
2576 for(int k=0;k<nbOfComp;k++)
2577 { double delta=inDataOther[k]-inData[j*nbOfComp+k]; dist+=delta*delta; }
2579 outData[i*nbOfTuples+j]=dist;
2586 * Sorts value within every tuple of \a this array.
2587 * \param [in] asc - if \a true, the values are sorted in ascending order, else,
2588 * in descending order.
2589 * \throw If \a this is not allocated.
2591 void DataArrayDouble::sortPerTuple(bool asc)
2594 double *pt=getPointer();
2595 int nbOfTuple=getNumberOfTuples();
2596 int nbOfComp=getNumberOfComponents();
2598 for(int i=0;i<nbOfTuple;i++,pt+=nbOfComp)
2599 std::sort(pt,pt+nbOfComp);
2601 for(int i=0;i<nbOfTuple;i++,pt+=nbOfComp)
2602 std::sort(pt,pt+nbOfComp,std::greater<double>());
2607 * Converts every value of \a this array to its absolute value.
2608 * \b WARNING this method is non const. If a new DataArrayDouble instance should be built containing the result of abs DataArrayDouble::computeAbs
2609 * should be called instead.
2611 * \throw If \a this is not allocated.
2612 * \sa DataArrayDouble::computeAbs
2614 void DataArrayDouble::abs()
2617 double *ptr(getPointer());
2618 std::size_t nbOfElems(getNbOfElems());
2619 std::transform(ptr,ptr+nbOfElems,ptr,std::ptr_fun<double,double>(fabs));
2624 * This method builds a new instance of \a this object containing the result of std::abs applied of all elements in \a this.
2625 * This method is a const method (that do not change any values in \a this) contrary to DataArrayDouble::abs method.
2627 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2628 * same number of tuples and component as \a this array.
2629 * The caller is to delete this result array using decrRef() as it is no more
2631 * \throw If \a this is not allocated.
2632 * \sa DataArrayDouble::abs
2634 DataArrayDouble *DataArrayDouble::computeAbs() const
2637 DataArrayDouble *newArr(DataArrayDouble::New());
2638 int nbOfTuples(getNumberOfTuples());
2639 int nbOfComp(getNumberOfComponents());
2640 newArr->alloc(nbOfTuples,nbOfComp);
2641 std::transform(begin(),end(),newArr->getPointer(),std::ptr_fun<double,double>(fabs));
2642 newArr->copyStringInfoFrom(*this);
2647 * Modify all elements of \a this array, so that
2648 * an element _x_ becomes \f$ numerator / x \f$.
2649 * \warning If an exception is thrown because of presence of 0.0 element in \a this
2650 * array, all elements processed before detection of the zero element remain
2652 * \param [in] numerator - the numerator used to modify array elements.
2653 * \throw If \a this is not allocated.
2654 * \throw If there is an element equal to 0.0 in \a this array.
2656 void DataArrayDouble::applyInv(double numerator)
2659 double *ptr=getPointer();
2660 std::size_t nbOfElems=getNbOfElems();
2661 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2663 if(std::abs(*ptr)>std::numeric_limits<double>::min())
2665 *ptr=numerator/(*ptr);
2669 std::ostringstream oss; oss << "DataArrayDouble::applyInv : presence of null value in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
2671 throw INTERP_KERNEL::Exception(oss.str().c_str());
2678 * Modify all elements of \a this array, so that
2679 * an element _x_ becomes <em> val ^ x </em>. Contrary to DataArrayInt::applyPow
2680 * all values in \a this have to be >= 0 if val is \b not integer.
2681 * \param [in] val - the value used to apply pow on all array elements.
2682 * \throw If \a this is not allocated.
2683 * \warning If an exception is thrown because of presence of 0 element in \a this
2684 * array and \a val is \b not integer, all elements processed before detection of the zero element remain
2687 void DataArrayDouble::applyPow(double val)
2690 double *ptr=getPointer();
2691 std::size_t nbOfElems=getNbOfElems();
2693 bool isInt=((double)val2)==val;
2696 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2702 std::ostringstream oss; oss << "DataArrayDouble::applyPow (double) : At elem # " << i << " value is " << *ptr << " ! must be >=0. !";
2703 throw INTERP_KERNEL::Exception(oss.str().c_str());
2709 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2710 *ptr=pow(*ptr,val2);
2716 * Modify all elements of \a this array, so that
2717 * an element _x_ becomes \f$ val ^ x \f$.
2718 * \param [in] val - the value used to apply pow on all array elements.
2719 * \throw If \a this is not allocated.
2720 * \throw If \a val < 0.
2721 * \warning If an exception is thrown because of presence of 0 element in \a this
2722 * array, all elements processed before detection of the zero element remain
2725 void DataArrayDouble::applyRPow(double val)
2729 throw INTERP_KERNEL::Exception("DataArrayDouble::applyRPow : the input value has to be >= 0 !");
2730 double *ptr=getPointer();
2731 std::size_t nbOfElems=getNbOfElems();
2732 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2738 * Returns a new DataArrayDouble created from \a this one by applying \a
2739 * FunctionToEvaluate to every tuple of \a this array. Textual data is not copied.
2740 * For more info see \ref MEDCouplingArrayApplyFunc
2741 * \param [in] nbOfComp - number of components in the result array.
2742 * \param [in] func - the \a FunctionToEvaluate declared as
2743 * \c bool (*\a func)(\c const \c double *\a pos, \c double *\a res),
2744 * where \a pos points to the first component of a tuple of \a this array
2745 * and \a res points to the first component of a tuple of the result array.
2746 * Note that length (number of components) of \a pos can differ from
2748 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2749 * same number of tuples as \a this array.
2750 * The caller is to delete this result array using decrRef() as it is no more
2752 * \throw If \a this is not allocated.
2753 * \throw If \a func returns \a false.
2755 DataArrayDouble *DataArrayDouble::applyFunc(int nbOfComp, FunctionToEvaluate func) const
2758 DataArrayDouble *newArr=DataArrayDouble::New();
2759 int nbOfTuples=getNumberOfTuples();
2760 int oldNbOfComp=getNumberOfComponents();
2761 newArr->alloc(nbOfTuples,nbOfComp);
2762 const double *ptr=getConstPointer();
2763 double *ptrToFill=newArr->getPointer();
2764 for(int i=0;i<nbOfTuples;i++)
2766 if(!func(ptr+i*oldNbOfComp,ptrToFill+i*nbOfComp))
2768 std::ostringstream oss; oss << "For tuple # " << i << " with value (";
2769 std::copy(ptr+oldNbOfComp*i,ptr+oldNbOfComp*(i+1),std::ostream_iterator<double>(oss,", "));
2770 oss << ") : Evaluation of function failed !";
2772 throw INTERP_KERNEL::Exception(oss.str().c_str());
2779 * Returns a new DataArrayDouble created from \a this one by applying a function to every
2780 * tuple of \a this array. Textual data is not copied.
2781 * For more info see \ref MEDCouplingArrayApplyFunc1.
2782 * \param [in] nbOfComp - number of components in the result array.
2783 * \param [in] func - the expression defining how to transform a tuple of \a this array.
2784 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
2785 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
2786 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
2787 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2788 * same number of tuples as \a this array and \a nbOfComp components.
2789 * The caller is to delete this result array using decrRef() as it is no more
2791 * \throw If \a this is not allocated.
2792 * \throw If computing \a func fails.
2794 DataArrayDouble *DataArrayDouble::applyFunc(int nbOfComp, const std::string& func, bool isSafe) const
2796 INTERP_KERNEL::ExprParser expr(func);
2798 std::set<std::string> vars;
2799 expr.getTrueSetOfVars(vars);
2800 std::vector<std::string> varsV(vars.begin(),vars.end());
2801 return applyFuncNamedCompo(nbOfComp,varsV,func,isSafe);
2805 * Returns a new DataArrayDouble created from \a this one by applying a function to every
2806 * tuple of \a this array. Textual data is not copied. This method works by tuples (whatever its size).
2807 * If \a this is a one component array, call applyFuncOnThis instead that performs the same work faster.
2809 * For more info see \ref MEDCouplingArrayApplyFunc0.
2810 * \param [in] func - the expression defining how to transform a tuple of \a this array.
2811 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
2812 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
2813 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
2814 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2815 * same number of tuples and components as \a this array.
2816 * The caller is to delete this result array using decrRef() as it is no more
2818 * \sa applyFuncOnThis
2819 * \throw If \a this is not allocated.
2820 * \throw If computing \a func fails.
2822 DataArrayDouble *DataArrayDouble::applyFunc(const std::string& func, bool isSafe) const
2824 int nbOfComp(getNumberOfComponents());
2826 throw INTERP_KERNEL::Exception("DataArrayDouble::applyFunc : output number of component must be > 0 !");
2828 int nbOfTuples(getNumberOfTuples());
2829 MCAuto<DataArrayDouble> newArr(DataArrayDouble::New());
2830 newArr->alloc(nbOfTuples,nbOfComp);
2831 INTERP_KERNEL::ExprParser expr(func);
2833 std::set<std::string> vars;
2834 expr.getTrueSetOfVars(vars);
2835 if((int)vars.size()>1)
2837 std::ostringstream oss; oss << "DataArrayDouble::applyFunc : this method works only with at most one var func expression ! If you need to map comps on variables please use applyFuncCompo or applyFuncNamedCompo instead ! Vars in expr are : ";
2838 std::copy(vars.begin(),vars.end(),std::ostream_iterator<std::string>(oss," "));
2839 throw INTERP_KERNEL::Exception(oss.str().c_str());
2843 expr.prepareFastEvaluator();
2844 newArr->rearrange(1);
2845 newArr->fillWithValue(expr.evaluateDouble());
2846 newArr->rearrange(nbOfComp);
2847 return newArr.retn();
2849 std::vector<std::string> vars2(vars.begin(),vars.end());
2850 double buff,*ptrToFill(newArr->getPointer());
2851 const double *ptr(begin());
2852 std::vector<double> stck;
2853 expr.prepareExprEvaluationDouble(vars2,1,1,0,&buff,&buff+1);
2854 expr.prepareFastEvaluator();
2857 for(int i=0;i<nbOfTuples;i++)
2859 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
2862 expr.evaluateDoubleInternal(stck);
2863 *ptrToFill=stck.back();
2870 for(int i=0;i<nbOfTuples;i++)
2872 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
2877 expr.evaluateDoubleInternalSafe(stck);
2879 catch(INTERP_KERNEL::Exception& e)
2881 std::ostringstream oss; oss << "For tuple # " << i << " component # " << iComp << " with value (";
2883 oss << ") : Evaluation of function failed !" << e.what();
2884 throw INTERP_KERNEL::Exception(oss.str().c_str());
2886 *ptrToFill=stck.back();
2891 return newArr.retn();
2895 * This method is a non const method that modify the array in \a this.
2896 * This method only works on one component array. It means that function \a func must
2897 * contain at most one variable.
2898 * This method is a specialization of applyFunc method with one parameter on one component array.
2900 * \param [in] func - the expression defining how to transform a tuple of \a this array.
2901 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
2902 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
2903 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
2907 void DataArrayDouble::applyFuncOnThis(const std::string& func, bool isSafe)
2909 int nbOfComp(getNumberOfComponents());
2911 throw INTERP_KERNEL::Exception("DataArrayDouble::applyFuncOnThis : output number of component must be > 0 !");
2913 int nbOfTuples(getNumberOfTuples());
2914 INTERP_KERNEL::ExprParser expr(func);
2916 std::set<std::string> vars;
2917 expr.getTrueSetOfVars(vars);
2918 if((int)vars.size()>1)
2920 std::ostringstream oss; oss << "DataArrayDouble::applyFuncOnThis : this method works only with at most one var func expression ! If you need to map comps on variables please use applyFuncCompo or applyFuncNamedCompo instead ! Vars in expr are : ";
2921 std::copy(vars.begin(),vars.end(),std::ostream_iterator<std::string>(oss," "));
2922 throw INTERP_KERNEL::Exception(oss.str().c_str());
2926 expr.prepareFastEvaluator();
2927 std::vector<std::string> compInfo(getInfoOnComponents());
2929 fillWithValue(expr.evaluateDouble());
2930 rearrange(nbOfComp);
2931 setInfoOnComponents(compInfo);
2934 std::vector<std::string> vars2(vars.begin(),vars.end());
2935 double buff,*ptrToFill(getPointer());
2936 const double *ptr(begin());
2937 std::vector<double> stck;
2938 expr.prepareExprEvaluationDouble(vars2,1,1,0,&buff,&buff+1);
2939 expr.prepareFastEvaluator();
2942 for(int i=0;i<nbOfTuples;i++)
2944 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
2947 expr.evaluateDoubleInternal(stck);
2948 *ptrToFill=stck.back();
2955 for(int i=0;i<nbOfTuples;i++)
2957 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
2962 expr.evaluateDoubleInternalSafe(stck);
2964 catch(INTERP_KERNEL::Exception& e)
2966 std::ostringstream oss; oss << "For tuple # " << i << " component # " << iComp << " with value (";
2968 oss << ") : Evaluation of function failed !" << e.what();
2969 throw INTERP_KERNEL::Exception(oss.str().c_str());
2971 *ptrToFill=stck.back();
2979 * Returns a new DataArrayDouble created from \a this one by applying a function to every
2980 * tuple of \a this array. Textual data is not copied.
2981 * For more info see \ref MEDCouplingArrayApplyFunc2.
2982 * \param [in] nbOfComp - number of components in the result array.
2983 * \param [in] func - the expression defining how to transform a tuple of \a this array.
2984 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
2985 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
2986 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
2987 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2988 * same number of tuples as \a this array.
2989 * The caller is to delete this result array using decrRef() as it is no more
2991 * \throw If \a this is not allocated.
2992 * \throw If \a func contains vars that are not in \a this->getInfoOnComponent().
2993 * \throw If computing \a func fails.
2995 DataArrayDouble *DataArrayDouble::applyFuncCompo(int nbOfComp, const std::string& func, bool isSafe) const
2997 return applyFuncNamedCompo(nbOfComp,getVarsOnComponent(),func,isSafe);
3001 * Returns a new DataArrayDouble created from \a this one by applying a function to every
3002 * tuple of \a this array. Textual data is not copied.
3003 * For more info see \ref MEDCouplingArrayApplyFunc3.
3004 * \param [in] nbOfComp - number of components in the result array.
3005 * \param [in] varsOrder - sequence of vars defining their order.
3006 * \param [in] func - the expression defining how to transform a tuple of \a this array.
3007 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
3008 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
3009 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
3010 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
3011 * same number of tuples as \a this array.
3012 * The caller is to delete this result array using decrRef() as it is no more
3014 * \throw If \a this is not allocated.
3015 * \throw If \a func contains vars not in \a varsOrder.
3016 * \throw If computing \a func fails.
3018 DataArrayDouble *DataArrayDouble::applyFuncNamedCompo(int nbOfComp, const std::vector<std::string>& varsOrder, const std::string& func, bool isSafe) const
3021 throw INTERP_KERNEL::Exception("DataArrayDouble::applyFuncNamedCompo : output number of component must be > 0 !");
3022 std::vector<std::string> varsOrder2(varsOrder);
3023 int oldNbOfComp(getNumberOfComponents());
3024 for(int i=(int)varsOrder.size();i<oldNbOfComp;i++)
3025 varsOrder2.push_back(std::string());
3027 int nbOfTuples(getNumberOfTuples());
3028 INTERP_KERNEL::ExprParser expr(func);
3030 std::set<std::string> vars;
3031 expr.getTrueSetOfVars(vars);
3032 if((int)vars.size()>oldNbOfComp)
3034 std::ostringstream oss; oss << "The field has " << oldNbOfComp << " components and there are ";
3035 oss << vars.size() << " variables : ";
3036 std::copy(vars.begin(),vars.end(),std::ostream_iterator<std::string>(oss," "));
3037 throw INTERP_KERNEL::Exception(oss.str().c_str());
3039 MCAuto<DataArrayDouble> newArr(DataArrayDouble::New());
3040 newArr->alloc(nbOfTuples,nbOfComp);
3041 INTERP_KERNEL::AutoPtr<double> buff(new double[oldNbOfComp]);
3042 double *buffPtr(buff),*ptrToFill;
3043 std::vector<double> stck;
3044 for(int iComp=0;iComp<nbOfComp;iComp++)
3046 expr.prepareExprEvaluationDouble(varsOrder2,oldNbOfComp,nbOfComp,iComp,buffPtr,buffPtr+oldNbOfComp);
3047 expr.prepareFastEvaluator();
3048 const double *ptr(getConstPointer());
3049 ptrToFill=newArr->getPointer()+iComp;
3052 for(int i=0;i<nbOfTuples;i++,ptrToFill+=nbOfComp,ptr+=oldNbOfComp)
3054 std::copy(ptr,ptr+oldNbOfComp,buffPtr);
3055 expr.evaluateDoubleInternal(stck);
3056 *ptrToFill=stck.back();
3062 for(int i=0;i<nbOfTuples;i++,ptrToFill+=nbOfComp,ptr+=oldNbOfComp)
3064 std::copy(ptr,ptr+oldNbOfComp,buffPtr);
3067 expr.evaluateDoubleInternalSafe(stck);
3068 *ptrToFill=stck.back();
3071 catch(INTERP_KERNEL::Exception& e)
3073 std::ostringstream oss; oss << "For tuple # " << i << " with value (";
3074 std::copy(ptr+oldNbOfComp*i,ptr+oldNbOfComp*(i+1),std::ostream_iterator<double>(oss,", "));
3075 oss << ") : Evaluation of function failed !" << e.what();
3076 throw INTERP_KERNEL::Exception(oss.str().c_str());
3081 return newArr.retn();
3084 void DataArrayDouble::applyFuncFast32(const std::string& func)
3087 INTERP_KERNEL::ExprParser expr(func);
3089 char *funcStr=expr.compileX86();
3091 *((void **)&funcPtr)=funcStr;//he he...
3093 double *ptr=getPointer();
3094 int nbOfComp=getNumberOfComponents();
3095 int nbOfTuples=getNumberOfTuples();
3096 int nbOfElems=nbOfTuples*nbOfComp;
3097 for(int i=0;i<nbOfElems;i++,ptr++)
3102 void DataArrayDouble::applyFuncFast64(const std::string& func)
3105 INTERP_KERNEL::ExprParser expr(func);
3107 char *funcStr=expr.compileX86_64();
3109 *((void **)&funcPtr)=funcStr;//he he...
3111 double *ptr=getPointer();
3112 int nbOfComp=getNumberOfComponents();
3113 int nbOfTuples=getNumberOfTuples();
3114 int nbOfElems=nbOfTuples*nbOfComp;
3115 for(int i=0;i<nbOfElems;i++,ptr++)
3121 * \return a new object that is the result of the symmetry along 3D plane defined by its normal vector \a normalVector and a point \a point.
3123 MCAuto<DataArrayDouble> DataArrayDouble::symmetry3DPlane(const double point[3], const double normalVector[3]) const
3126 if(getNumberOfComponents()!=3)
3127 throw INTERP_KERNEL::Exception("DataArrayDouble::symmetry3DPlane : this is excepted to have 3 components !");
3128 int nbTuples(getNumberOfTuples());
3129 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
3130 ret->alloc(nbTuples,3);
3131 Symmetry3DPlane(point,normalVector,nbTuples,begin(),ret->getPointer());
3135 DataArrayDoubleIterator *DataArrayDouble::iterator()
3137 return new DataArrayDoubleIterator(this);
3141 * Returns a new DataArrayInt contating indices of tuples of \a this one-dimensional
3142 * array whose values are within a given range. Textual data is not copied.
3143 * \param [in] vmin - a lowest acceptable value (included).
3144 * \param [in] vmax - a greatest acceptable value (included).
3145 * \return DataArrayInt * - the new instance of DataArrayInt.
3146 * The caller is to delete this result array using decrRef() as it is no more
3148 * \throw If \a this->getNumberOfComponents() != 1.
3150 * \sa DataArrayDouble::findIdsNotInRange
3152 * \if ENABLE_EXAMPLES
3153 * \ref cpp_mcdataarraydouble_getidsinrange "Here is a C++ example".<br>
3154 * \ref py_mcdataarraydouble_getidsinrange "Here is a Python example".
3157 DataArrayInt *DataArrayDouble::findIdsInRange(double vmin, double vmax) const
3160 if(getNumberOfComponents()!=1)
3161 throw INTERP_KERNEL::Exception("DataArrayDouble::findIdsInRange : this must have exactly one component !");
3162 const double *cptr(begin());
3163 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
3164 int nbOfTuples(getNumberOfTuples());
3165 for(int i=0;i<nbOfTuples;i++,cptr++)
3166 if(*cptr>=vmin && *cptr<=vmax)
3167 ret->pushBackSilent(i);
3172 * Returns a new DataArrayInt contating indices of tuples of \a this one-dimensional
3173 * array whose values are not within a given range. Textual data is not copied.
3174 * \param [in] vmin - a lowest not acceptable value (excluded).
3175 * \param [in] vmax - a greatest not acceptable value (excluded).
3176 * \return DataArrayInt * - the new instance of DataArrayInt.
3177 * The caller is to delete this result array using decrRef() as it is no more
3179 * \throw If \a this->getNumberOfComponents() != 1.
3181 * \sa DataArrayDouble::findIdsInRange
3183 DataArrayInt *DataArrayDouble::findIdsNotInRange(double vmin, double vmax) const
3186 if(getNumberOfComponents()!=1)
3187 throw INTERP_KERNEL::Exception("DataArrayDouble::findIdsNotInRange : this must have exactly one component !");
3188 const double *cptr(begin());
3189 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
3190 int nbOfTuples(getNumberOfTuples());
3191 for(int i=0;i<nbOfTuples;i++,cptr++)
3192 if(*cptr<vmin || *cptr>vmax)
3193 ret->pushBackSilent(i);
3198 * Returns a new DataArrayDouble by concatenating two given arrays, so that (1) the number
3199 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
3200 * the number of component in the result array is same as that of each of given arrays.
3201 * Info on components is copied from the first of the given arrays. Number of components
3202 * in the given arrays must be the same.
3203 * \param [in] a1 - an array to include in the result array.
3204 * \param [in] a2 - another array to include in the result array.
3205 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3206 * The caller is to delete this result array using decrRef() as it is no more
3208 * \throw If both \a a1 and \a a2 are NULL.
3209 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents().
3211 DataArrayDouble *DataArrayDouble::Aggregate(const DataArrayDouble *a1, const DataArrayDouble *a2)
3213 std::vector<const DataArrayDouble *> tmp(2);
3214 tmp[0]=a1; tmp[1]=a2;
3215 return Aggregate(tmp);
3219 * Returns a new DataArrayDouble by concatenating all given arrays, so that (1) the number
3220 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
3221 * the number of component in the result array is same as that of each of given arrays.
3222 * Info on components is copied from the first of the given arrays. Number of components
3223 * in the given arrays must be the same.
3224 * If the number of non null of elements in \a arr is equal to one the returned object is a copy of it
3225 * not the object itself.
3226 * \param [in] arr - a sequence of arrays to include in the result array.
3227 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3228 * The caller is to delete this result array using decrRef() as it is no more
3230 * \throw If all arrays within \a arr are NULL.
3231 * \throw If getNumberOfComponents() of arrays within \a arr.
3233 DataArrayDouble *DataArrayDouble::Aggregate(const std::vector<const DataArrayDouble *>& arr)
3235 std::vector<const DataArrayDouble *> a;
3236 for(std::vector<const DataArrayDouble *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
3240 throw INTERP_KERNEL::Exception("DataArrayDouble::Aggregate : input list must contain at least one NON EMPTY DataArrayDouble !");
3241 std::vector<const DataArrayDouble *>::const_iterator it=a.begin();
3242 int nbOfComp=(*it)->getNumberOfComponents();
3243 int nbt=(*it++)->getNumberOfTuples();
3244 for(int i=1;it!=a.end();it++,i++)
3246 if((*it)->getNumberOfComponents()!=nbOfComp)
3247 throw INTERP_KERNEL::Exception("DataArrayDouble::Aggregate : Nb of components mismatch for array aggregation !");
3248 nbt+=(*it)->getNumberOfTuples();
3250 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
3251 ret->alloc(nbt,nbOfComp);
3252 double *pt=ret->getPointer();
3253 for(it=a.begin();it!=a.end();it++)
3254 pt=std::copy((*it)->getConstPointer(),(*it)->getConstPointer()+(*it)->getNbOfElems(),pt);
3255 ret->copyStringInfoFrom(*(a[0]));
3260 * Returns a new DataArrayDouble containing a dot product of two given arrays, so that
3261 * the i-th tuple of the result array is a sum of products of j-th components of i-th
3262 * tuples of given arrays (\f$ a_i = \sum_{j=1}^n a1_j * a2_j \f$).
3263 * Info on components and name is copied from the first of the given arrays.
3264 * Number of tuples and components in the given arrays must be the same.
3265 * \param [in] a1 - a given array.
3266 * \param [in] a2 - another given array.
3267 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3268 * The caller is to delete this result array using decrRef() as it is no more
3270 * \throw If either \a a1 or \a a2 is NULL.
3271 * \throw If any given array is not allocated.
3272 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3273 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents()
3275 DataArrayDouble *DataArrayDouble::Dot(const DataArrayDouble *a1, const DataArrayDouble *a2)
3278 throw INTERP_KERNEL::Exception("DataArrayDouble::Dot : input DataArrayDouble instance is NULL !");
3279 a1->checkAllocated();
3280 a2->checkAllocated();
3281 int nbOfComp=a1->getNumberOfComponents();
3282 if(nbOfComp!=a2->getNumberOfComponents())
3283 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Dot !");
3284 int nbOfTuple=a1->getNumberOfTuples();
3285 if(nbOfTuple!=a2->getNumberOfTuples())
3286 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Dot !");
3287 DataArrayDouble *ret=DataArrayDouble::New();
3288 ret->alloc(nbOfTuple,1);
3289 double *retPtr=ret->getPointer();
3290 const double *a1Ptr=a1->getConstPointer();
3291 const double *a2Ptr=a2->getConstPointer();
3292 for(int i=0;i<nbOfTuple;i++)
3295 for(int j=0;j<nbOfComp;j++)
3296 sum+=a1Ptr[i*nbOfComp+j]*a2Ptr[i*nbOfComp+j];
3299 ret->setInfoOnComponent(0,a1->getInfoOnComponent(0));
3300 ret->setName(a1->getName());
3305 * Returns a new DataArrayDouble containing a cross product of two given arrays, so that
3306 * the i-th tuple of the result array contains 3 components of a vector which is a cross
3307 * product of two vectors defined by the i-th tuples of given arrays.
3308 * Info on components is copied from the first of the given arrays.
3309 * Number of tuples in the given arrays must be the same.
3310 * Number of components in the given arrays must be 3.
3311 * \param [in] a1 - a given array.
3312 * \param [in] a2 - another given array.
3313 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3314 * The caller is to delete this result array using decrRef() as it is no more
3316 * \throw If either \a a1 or \a a2 is NULL.
3317 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3318 * \throw If \a a1->getNumberOfComponents() != 3
3319 * \throw If \a a2->getNumberOfComponents() != 3
3321 DataArrayDouble *DataArrayDouble::CrossProduct(const DataArrayDouble *a1, const DataArrayDouble *a2)
3324 throw INTERP_KERNEL::Exception("DataArrayDouble::CrossProduct : input DataArrayDouble instance is NULL !");
3325 int nbOfComp=a1->getNumberOfComponents();
3326 if(nbOfComp!=a2->getNumberOfComponents())
3327 throw INTERP_KERNEL::Exception("Nb of components mismatch for array crossProduct !");
3329 throw INTERP_KERNEL::Exception("Nb of components must be equal to 3 for array crossProduct !");
3330 int nbOfTuple=a1->getNumberOfTuples();
3331 if(nbOfTuple!=a2->getNumberOfTuples())
3332 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array crossProduct !");
3333 DataArrayDouble *ret=DataArrayDouble::New();
3334 ret->alloc(nbOfTuple,3);
3335 double *retPtr=ret->getPointer();
3336 const double *a1Ptr=a1->getConstPointer();
3337 const double *a2Ptr=a2->getConstPointer();
3338 for(int i=0;i<nbOfTuple;i++)
3340 retPtr[3*i]=a1Ptr[3*i+1]*a2Ptr[3*i+2]-a1Ptr[3*i+2]*a2Ptr[3*i+1];
3341 retPtr[3*i+1]=a1Ptr[3*i+2]*a2Ptr[3*i]-a1Ptr[3*i]*a2Ptr[3*i+2];
3342 retPtr[3*i+2]=a1Ptr[3*i]*a2Ptr[3*i+1]-a1Ptr[3*i+1]*a2Ptr[3*i];
3344 ret->copyStringInfoFrom(*a1);
3349 * Returns a new DataArrayDouble containing maximal values of two given arrays.
3350 * Info on components is copied from the first of the given arrays.
3351 * Number of tuples and components in the given arrays must be the same.
3352 * \param [in] a1 - an array to compare values with another one.
3353 * \param [in] a2 - another array to compare values with the first one.
3354 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3355 * The caller is to delete this result array using decrRef() as it is no more
3357 * \throw If either \a a1 or \a a2 is NULL.
3358 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3359 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents()
3361 DataArrayDouble *DataArrayDouble::Max(const DataArrayDouble *a1, const DataArrayDouble *a2)
3364 throw INTERP_KERNEL::Exception("DataArrayDouble::Max : input DataArrayDouble instance is NULL !");
3365 int nbOfComp=a1->getNumberOfComponents();
3366 if(nbOfComp!=a2->getNumberOfComponents())
3367 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Max !");
3368 int nbOfTuple=a1->getNumberOfTuples();
3369 if(nbOfTuple!=a2->getNumberOfTuples())
3370 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Max !");
3371 DataArrayDouble *ret=DataArrayDouble::New();
3372 ret->alloc(nbOfTuple,nbOfComp);
3373 double *retPtr=ret->getPointer();
3374 const double *a1Ptr=a1->getConstPointer();
3375 const double *a2Ptr=a2->getConstPointer();
3376 int nbElem=nbOfTuple*nbOfComp;
3377 for(int i=0;i<nbElem;i++)
3378 retPtr[i]=std::max(a1Ptr[i],a2Ptr[i]);
3379 ret->copyStringInfoFrom(*a1);
3384 * Returns a new DataArrayDouble containing minimal values of two given arrays.
3385 * Info on components is copied from the first of the given arrays.
3386 * Number of tuples and components in the given arrays must be the same.
3387 * \param [in] a1 - an array to compare values with another one.
3388 * \param [in] a2 - another array to compare values with the first one.
3389 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3390 * The caller is to delete this result array using decrRef() as it is no more
3392 * \throw If either \a a1 or \a a2 is NULL.
3393 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3394 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents()
3396 DataArrayDouble *DataArrayDouble::Min(const DataArrayDouble *a1, const DataArrayDouble *a2)
3399 throw INTERP_KERNEL::Exception("DataArrayDouble::Min : input DataArrayDouble instance is NULL !");
3400 int nbOfComp=a1->getNumberOfComponents();
3401 if(nbOfComp!=a2->getNumberOfComponents())
3402 throw INTERP_KERNEL::Exception("Nb of components mismatch for array min !");
3403 int nbOfTuple=a1->getNumberOfTuples();
3404 if(nbOfTuple!=a2->getNumberOfTuples())
3405 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array min !");
3406 DataArrayDouble *ret=DataArrayDouble::New();
3407 ret->alloc(nbOfTuple,nbOfComp);
3408 double *retPtr=ret->getPointer();
3409 const double *a1Ptr=a1->getConstPointer();
3410 const double *a2Ptr=a2->getConstPointer();
3411 int nbElem=nbOfTuple*nbOfComp;
3412 for(int i=0;i<nbElem;i++)
3413 retPtr[i]=std::min(a1Ptr[i],a2Ptr[i]);
3414 ret->copyStringInfoFrom(*a1);
3419 * Returns a new DataArrayDouble that is the result of pow of two given arrays. There are 3
3422 * \param [in] a1 - an array to pow up.
3423 * \param [in] a2 - another array to sum up.
3424 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3425 * The caller is to delete this result array using decrRef() as it is no more
3427 * \throw If either \a a1 or \a a2 is NULL.
3428 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3429 * \throw If \a a1->getNumberOfComponents() != 1 or \a a2->getNumberOfComponents() != 1.
3430 * \throw If there is a negative value in \a a1.
3432 DataArrayDouble *DataArrayDouble::Pow(const DataArrayDouble *a1, const DataArrayDouble *a2)
3435 throw INTERP_KERNEL::Exception("DataArrayDouble::Pow : at least one of input instances is null !");
3436 int nbOfTuple=a1->getNumberOfTuples();
3437 int nbOfTuple2=a2->getNumberOfTuples();
3438 int nbOfComp=a1->getNumberOfComponents();
3439 int nbOfComp2=a2->getNumberOfComponents();
3440 if(nbOfTuple!=nbOfTuple2)
3441 throw INTERP_KERNEL::Exception("DataArrayDouble::Pow : number of tuples mismatches !");
3442 if(nbOfComp!=1 || nbOfComp2!=1)
3443 throw INTERP_KERNEL::Exception("DataArrayDouble::Pow : number of components of both arrays must be equal to 1 !");
3444 MCAuto<DataArrayDouble> ret=DataArrayDouble::New(); ret->alloc(nbOfTuple,1);
3445 const double *ptr1(a1->begin()),*ptr2(a2->begin());
3446 double *ptr=ret->getPointer();
3447 for(int i=0;i<nbOfTuple;i++,ptr1++,ptr2++,ptr++)
3451 *ptr=pow(*ptr1,*ptr2);
3455 std::ostringstream oss; oss << "DataArrayDouble::Pow : on tuple #" << i << " of a1 value is < 0 (" << *ptr1 << ") !";
3456 throw INTERP_KERNEL::Exception(oss.str().c_str());
3463 * Apply pow on values of another DataArrayDouble to values of \a this one.
3465 * \param [in] other - an array to pow to \a this one.
3466 * \throw If \a other is NULL.
3467 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples()
3468 * \throw If \a this->getNumberOfComponents() != 1 or \a other->getNumberOfComponents() != 1
3469 * \throw If there is a negative value in \a this.
3471 void DataArrayDouble::powEqual(const DataArrayDouble *other)
3474 throw INTERP_KERNEL::Exception("DataArrayDouble::powEqual : input instance is null !");
3475 int nbOfTuple=getNumberOfTuples();
3476 int nbOfTuple2=other->getNumberOfTuples();
3477 int nbOfComp=getNumberOfComponents();
3478 int nbOfComp2=other->getNumberOfComponents();
3479 if(nbOfTuple!=nbOfTuple2)
3480 throw INTERP_KERNEL::Exception("DataArrayDouble::powEqual : number of tuples mismatches !");
3481 if(nbOfComp!=1 || nbOfComp2!=1)
3482 throw INTERP_KERNEL::Exception("DataArrayDouble::powEqual : number of components of both arrays must be equal to 1 !");
3483 double *ptr=getPointer();
3484 const double *ptrc=other->begin();
3485 for(int i=0;i<nbOfTuple;i++,ptrc++,ptr++)
3488 *ptr=pow(*ptr,*ptrc);
3491 std::ostringstream oss; oss << "DataArrayDouble::powEqual : on tuple #" << i << " of this value is < 0 (" << *ptr << ") !";
3492 throw INTERP_KERNEL::Exception(oss.str().c_str());
3499 * This method is \b NOT wrapped into python because it can be useful only for performance reasons in C++ context.
3500 * All values in \a this must be 0. or 1. within eps error. 0 means false, 1 means true.
3501 * If an another value than 0 or 1 appear (within eps precision) an INTERP_KERNEL::Exception will be thrown.
3503 * \throw if \a this is not allocated.
3504 * \throw if \a this has not exactly one component.
3506 std::vector<bool> DataArrayDouble::toVectorOfBool(double eps) const
3509 if(getNumberOfComponents()!=1)
3510 throw INTERP_KERNEL::Exception("DataArrayDouble::toVectorOfBool : must be applied on single component array !");
3511 int nbt(getNumberOfTuples());
3512 std::vector<bool> ret(nbt);
3513 const double *pt(begin());
3514 for(int i=0;i<nbt;i++)
3518 else if(fabs(pt[i]-1.)<eps)
3522 std::ostringstream oss; oss << "DataArrayDouble::toVectorOfBool : the tuple #" << i << " has value " << pt[i] << " is invalid ! must be 0. or 1. !";
3523 throw INTERP_KERNEL::Exception(oss.str().c_str());
3530 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
3533 void DataArrayDouble::getTinySerializationIntInformation(std::vector<int>& tinyInfo) const
3538 tinyInfo[0]=getNumberOfTuples();
3539 tinyInfo[1]=getNumberOfComponents();
3549 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
3552 void DataArrayDouble::getTinySerializationStrInformation(std::vector<std::string>& tinyInfo) const
3556 int nbOfCompo=getNumberOfComponents();
3557 tinyInfo.resize(nbOfCompo+1);
3558 tinyInfo[0]=getName();
3559 for(int i=0;i<nbOfCompo;i++)
3560 tinyInfo[i+1]=getInfoOnComponent(i);
3565 tinyInfo[0]=getName();
3570 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
3571 * This method returns if a feeding is needed.
3573 bool DataArrayDouble::resizeForUnserialization(const std::vector<int>& tinyInfoI)
3575 int nbOfTuple=tinyInfoI[0];
3576 int nbOfComp=tinyInfoI[1];
3577 if(nbOfTuple!=-1 || nbOfComp!=-1)
3579 alloc(nbOfTuple,nbOfComp);
3586 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
3588 void DataArrayDouble::finishUnserialization(const std::vector<int>& tinyInfoI, const std::vector<std::string>& tinyInfoS)
3590 setName(tinyInfoS[0]);
3593 int nbOfCompo=getNumberOfComponents();
3594 for(int i=0;i<nbOfCompo;i++)
3595 setInfoOnComponent(i,tinyInfoS[i+1]);
3600 * Low static method that operates 3D rotation of 'nbNodes' 3D nodes whose coordinates are arranged in \a coordsIn
3601 * around an axe ( \a center, \a vect) and with angle \a angle.
3603 void DataArrayDouble::Rotate3DAlg(const double *center, const double *vect, double angle, int nbNodes, const double *coordsIn, double *coordsOut)
3605 if(!center || !vect)
3606 throw INTERP_KERNEL::Exception("DataArrayDouble::Rotate3DAlg : null vector in input !");
3607 double sina(sin(angle));
3608 double cosa(cos(angle));
3609 double vectorNorm[3];
3611 double matrixTmp[9];
3612 double norm(sqrt(vect[0]*vect[0]+vect[1]*vect[1]+vect[2]*vect[2]));
3613 if(norm<std::numeric_limits<double>::min())
3614 throw INTERP_KERNEL::Exception("DataArrayDouble::Rotate3DAlg : magnitude of input vector is too close of 0. !");
3615 std::transform(vect,vect+3,vectorNorm,std::bind2nd(std::multiplies<double>(),1/norm));
3616 //rotation matrix computation
3617 matrix[0]=cosa; matrix[1]=0.; matrix[2]=0.; matrix[3]=0.; matrix[4]=cosa; matrix[5]=0.; matrix[6]=0.; matrix[7]=0.; matrix[8]=cosa;
3618 matrixTmp[0]=vectorNorm[0]*vectorNorm[0]; matrixTmp[1]=vectorNorm[0]*vectorNorm[1]; matrixTmp[2]=vectorNorm[0]*vectorNorm[2];
3619 matrixTmp[3]=vectorNorm[1]*vectorNorm[0]; matrixTmp[4]=vectorNorm[1]*vectorNorm[1]; matrixTmp[5]=vectorNorm[1]*vectorNorm[2];
3620 matrixTmp[6]=vectorNorm[2]*vectorNorm[0]; matrixTmp[7]=vectorNorm[2]*vectorNorm[1]; matrixTmp[8]=vectorNorm[2]*vectorNorm[2];
3621 std::transform(matrixTmp,matrixTmp+9,matrixTmp,std::bind2nd(std::multiplies<double>(),1-cosa));
3622 std::transform(matrix,matrix+9,matrixTmp,matrix,std::plus<double>());
3623 matrixTmp[0]=0.; matrixTmp[1]=-vectorNorm[2]; matrixTmp[2]=vectorNorm[1];
3624 matrixTmp[3]=vectorNorm[2]; matrixTmp[4]=0.; matrixTmp[5]=-vectorNorm[0];
3625 matrixTmp[6]=-vectorNorm[1]; matrixTmp[7]=vectorNorm[0]; matrixTmp[8]=0.;
3626 std::transform(matrixTmp,matrixTmp+9,matrixTmp,std::bind2nd(std::multiplies<double>(),sina));
3627 std::transform(matrix,matrix+9,matrixTmp,matrix,std::plus<double>());
3628 //rotation matrix computed.
3630 for(int i=0; i<nbNodes; i++)
3632 std::transform(coordsIn+i*3,coordsIn+(i+1)*3,center,tmp,std::minus<double>());
3633 coordsOut[i*3]=matrix[0]*tmp[0]+matrix[1]*tmp[1]+matrix[2]*tmp[2]+center[0];
3634 coordsOut[i*3+1]=matrix[3]*tmp[0]+matrix[4]*tmp[1]+matrix[5]*tmp[2]+center[1];
3635 coordsOut[i*3+2]=matrix[6]*tmp[0]+matrix[7]*tmp[1]+matrix[8]*tmp[2]+center[2];
3639 void DataArrayDouble::Symmetry3DPlane(const double point[3], const double normalVector[3], int nbNodes, const double *coordsIn, double *coordsOut)
3641 double matrix[9],matrix2[9],matrix3[9];
3642 double vect[3],crossVect[3];
3643 INTERP_KERNEL::orthogonalVect3(normalVector,vect);
3644 crossVect[0]=normalVector[1]*vect[2]-normalVector[2]*vect[1];
3645 crossVect[1]=normalVector[2]*vect[0]-normalVector[0]*vect[2];
3646 crossVect[2]=normalVector[0]*vect[1]-normalVector[1]*vect[0];
3647 double nv(INTERP_KERNEL::norm<3>(vect)),ni(INTERP_KERNEL::norm<3>(normalVector)),nc(INTERP_KERNEL::norm<3>(crossVect));
3648 matrix[0]=vect[0]/nv; matrix[1]=crossVect[0]/nc; matrix[2]=-normalVector[0]/ni;
3649 matrix[3]=vect[1]/nv; matrix[4]=crossVect[1]/nc; matrix[5]=-normalVector[1]/ni;
3650 matrix[6]=vect[2]/nv; matrix[7]=crossVect[2]/nc; matrix[8]=-normalVector[2]/ni;
3651 matrix2[0]=vect[0]/nv; matrix2[1]=vect[1]/nv; matrix2[2]=vect[2]/nv;
3652 matrix2[3]=crossVect[0]/nc; matrix2[4]=crossVect[1]/nc; matrix2[5]=crossVect[2]/nc;
3653 matrix2[6]=normalVector[0]/ni; matrix2[7]=normalVector[1]/ni; matrix2[8]=normalVector[2]/ni;
3654 for(int i=0;i<3;i++)
3655 for(int j=0;j<3;j++)
3658 for(int k=0;k<3;k++)
3659 val+=matrix[3*i+k]*matrix2[3*k+j];
3662 //rotation matrix computed.
3664 for(int i=0; i<nbNodes; i++)
3666 std::transform(coordsIn+i*3,coordsIn+(i+1)*3,point,tmp,std::minus<double>());
3667 coordsOut[i*3]=matrix3[0]*tmp[0]+matrix3[1]*tmp[1]+matrix3[2]*tmp[2]+point[0];
3668 coordsOut[i*3+1]=matrix3[3]*tmp[0]+matrix3[4]*tmp[1]+matrix3[5]*tmp[2]+point[1];
3669 coordsOut[i*3+2]=matrix3[6]*tmp[0]+matrix3[7]*tmp[1]+matrix3[8]*tmp[2]+point[2];
3673 void DataArrayDouble::GiveBaseForPlane(const double normalVector[3], double baseOfPlane[9])
3675 double vect[3],crossVect[3];
3676 INTERP_KERNEL::orthogonalVect3(normalVector,vect);
3677 crossVect[0]=normalVector[1]*vect[2]-normalVector[2]*vect[1];
3678 crossVect[1]=normalVector[2]*vect[0]-normalVector[0]*vect[2];
3679 crossVect[2]=normalVector[0]*vect[1]-normalVector[1]*vect[0];
3680 double nv(INTERP_KERNEL::norm<3>(vect)),ni(INTERP_KERNEL::norm<3>(normalVector)),nc(INTERP_KERNEL::norm<3>(crossVect));
3681 baseOfPlane[0]=vect[0]/nv; baseOfPlane[1]=vect[1]/nv; baseOfPlane[2]=vect[2]/nv;
3682 baseOfPlane[3]=crossVect[0]/nc; baseOfPlane[4]=crossVect[1]/nc; baseOfPlane[5]=crossVect[2]/nc;
3683 baseOfPlane[6]=normalVector[0]/ni; baseOfPlane[7]=normalVector[1]/ni; baseOfPlane[8]=normalVector[2]/ni;
3687 * Low static method that operates 3D rotation of \a nbNodes 3D nodes whose coordinates are arranged in \a coords
3688 * around the center point \a center and with angle \a angle.
3690 void DataArrayDouble::Rotate2DAlg(const double *center, double angle, int nbNodes, const double *coordsIn, double *coordsOut)
3692 double cosa=cos(angle);
3693 double sina=sin(angle);
3695 matrix[0]=cosa; matrix[1]=-sina; matrix[2]=sina; matrix[3]=cosa;
3697 for(int i=0; i<nbNodes; i++)
3699 std::transform(coordsIn+i*2,coordsIn+(i+1)*2,center,tmp,std::minus<double>());
3700 coordsOut[i*2]=matrix[0]*tmp[0]+matrix[1]*tmp[1]+center[0];
3701 coordsOut[i*2+1]=matrix[2]*tmp[0]+matrix[3]*tmp[1]+center[1];
3705 DataArrayDoubleIterator::DataArrayDoubleIterator(DataArrayDouble *da):DataArrayIterator<double>(da)
3709 DataArrayDoubleTuple::DataArrayDoubleTuple(double *pt, int nbOfComp):DataArrayTuple<double>(pt,nbOfComp)
3714 std::string DataArrayDoubleTuple::repr() const
3716 std::ostringstream oss; oss.precision(17); oss << "(";
3717 for(int i=0;i<_nb_of_compo-1;i++)
3718 oss << _pt[i] << ", ";
3719 oss << _pt[_nb_of_compo-1] << ")";
3723 double DataArrayDoubleTuple::doubleValue() const
3725 return this->zeValue();
3729 * This method returns a newly allocated instance the caller should dealed with by a MEDCoupling::DataArrayDouble::decrRef.
3730 * This method performs \b no copy of data. The content is only referenced using MEDCoupling::DataArrayDouble::useArray with ownership set to \b false.
3731 * This method throws an INTERP_KERNEL::Exception is it is impossible to match sizes of \b this that is too say \b nbOfCompo=this->_nb_of_elem and \bnbOfTuples==1 or
3732 * \b nbOfCompo=1 and \bnbOfTuples==this->_nb_of_elem.
3734 DataArrayDouble *DataArrayDoubleTuple::buildDADouble(int nbOfTuples, int nbOfCompo) const
3736 return this->buildDA(nbOfTuples,nbOfCompo);
3740 * Returns a new instance of DataArrayInt. The caller is to delete this array
3741 * using decrRef() as it is no more needed.
3743 DataArrayInt *DataArrayInt::New()
3745 return new DataArrayInt;
3749 * Returns the only one value in \a this, if and only if number of elements
3750 * (nb of tuples * nb of components) is equal to 1, and that \a this is allocated.
3751 * \return double - the sole value stored in \a this array.
3752 * \throw If at least one of conditions stated above is not fulfilled.
3754 int DataArrayInt::intValue() const
3758 if(getNbOfElems()==1)
3760 return *getConstPointer();
3763 throw INTERP_KERNEL::Exception("DataArrayInt::intValue : DataArrayInt instance is allocated but number of elements is not equal to 1 !");
3766 throw INTERP_KERNEL::Exception("DataArrayInt::intValue : DataArrayInt instance is not allocated !");
3770 * Returns an integer value characterizing \a this array, which is useful for a quick
3771 * comparison of many instances of DataArrayInt.
3772 * \return int - the hash value.
3773 * \throw If \a this is not allocated.
3775 int DataArrayInt::getHashCode() const
3778 std::size_t nbOfElems=getNbOfElems();
3779 int ret=nbOfElems*65536;
3784 const int *pt=begin();
3785 for(std::size_t i=0;i<nbOfElems;i+=delta)
3786 ret0+=pt[i] & 0x1FFF;
3791 * Returns a full copy of \a this. For more info on copying data arrays see
3792 * \ref MEDCouplingArrayBasicsCopyDeep.
3793 * \return DataArrayInt * - a new instance of DataArrayInt.
3795 DataArrayInt *DataArrayInt::deepCopy() const
3797 return new DataArrayInt(*this);
3801 * Returns either a \a deep or \a shallow copy of this array. For more info see
3802 * \ref MEDCouplingArrayBasicsCopyDeep and \ref MEDCouplingArrayBasicsCopyShallow.
3803 * \param [in] dCpy - if \a true, a deep copy is returned, else, a shallow one.
3804 * \return DataArrayInt * - either a new instance of DataArrayInt (if \a dCpy
3805 * == \a true) or \a this instance (if \a dCpy == \a false).
3807 DataArrayInt *DataArrayInt::performCopyOrIncrRef(bool dCpy) const
3809 return DataArrayTemplateClassic<int>::PerformCopyOrIncrRef(dCpy,*this);
3813 * Assign zero to all values in \a this array. To know more on filling arrays see
3814 * \ref MEDCouplingArrayFill.
3815 * \throw If \a this is not allocated.
3817 void DataArrayInt::fillWithZero()
3823 * Set all values in \a this array so that the i-th element equals to \a init + i
3824 * (i starts from zero). To know more on filling arrays see \ref MEDCouplingArrayFill.
3825 * \param [in] init - value to assign to the first element of array.
3826 * \throw If \a this->getNumberOfComponents() != 1
3827 * \throw If \a this is not allocated.
3829 void DataArrayInt::iota(int init)
3832 if(getNumberOfComponents()!=1)
3833 throw INTERP_KERNEL::Exception("DataArrayInt::iota : works only for arrays with only one component, you can call 'rearrange' method before !");
3834 int *ptr=getPointer();
3835 int ntuples=getNumberOfTuples();
3836 for(int i=0;i<ntuples;i++)
3842 * Returns a textual and human readable representation of \a this instance of
3843 * DataArrayInt. This text is shown when a DataArrayInt is printed in Python.
3844 * \return std::string - text describing \a this DataArrayInt.
3846 * \sa reprNotTooLong, reprZip
3848 std::string DataArrayInt::repr() const
3850 std::ostringstream ret;
3855 std::string DataArrayInt::reprZip() const
3857 std::ostringstream ret;
3863 * This method is close to repr method except that when \a this has more than 1000 tuples, all tuples are not
3864 * printed out to avoid to consume too much space in interpretor.
3867 std::string DataArrayInt::reprNotTooLong() const
3869 std::ostringstream ret;
3870 reprNotTooLongStream(ret);
3874 void DataArrayInt::writeVTK(std::ostream& ofs, int indent, const std::string& type, const std::string& nameInFile, DataArrayByte *byteArr) const
3876 static const char SPACE[4]={' ',' ',' ',' '};
3878 std::string idt(indent,' ');
3879 ofs << idt << "<DataArray type=\"" << type << "\" Name=\"" << nameInFile << "\" NumberOfComponents=\"" << getNumberOfComponents() << "\"";
3882 ofs << " format=\"appended\" offset=\"" << byteArr->getNumberOfTuples() << "\">";
3883 if(std::string(type)=="Int32")
3885 const char *data(reinterpret_cast<const char *>(begin()));
3886 std::size_t sz(getNbOfElems()*sizeof(int));
3887 byteArr->insertAtTheEnd(data,data+sz);
3888 byteArr->insertAtTheEnd(SPACE,SPACE+4);
3890 else if(std::string(type)=="Int8")
3892 INTERP_KERNEL::AutoPtr<char> tmp(new char[getNbOfElems()]);
3893 std::copy(begin(),end(),(char *)tmp);
3894 byteArr->insertAtTheEnd((char *)tmp,(char *)tmp+getNbOfElems());
3895 byteArr->insertAtTheEnd(SPACE,SPACE+4);
3897 else if(std::string(type)=="UInt8")
3899 INTERP_KERNEL::AutoPtr<unsigned char> tmp(new unsigned char[getNbOfElems()]);
3900 std::copy(begin(),end(),(unsigned char *)tmp);
3901 byteArr->insertAtTheEnd((unsigned char *)tmp,(unsigned char *)tmp+getNbOfElems());
3902 byteArr->insertAtTheEnd(SPACE,SPACE+4);
3905 throw INTERP_KERNEL::Exception("DataArrayInt::writeVTK : Only Int32, Int8 and UInt8 supported !");
3909 ofs << " RangeMin=\"" << getMinValueInArray() << "\" RangeMax=\"" << getMaxValueInArray() << "\" format=\"ascii\">\n" << idt;
3910 std::copy(begin(),end(),std::ostream_iterator<int>(ofs," "));
3912 ofs << std::endl << idt << "</DataArray>\n";
3915 void DataArrayInt::reprStream(std::ostream& stream) const
3917 stream << "Name of int array : \"" << _name << "\"\n";
3918 reprWithoutNameStream(stream);
3921 void DataArrayInt::reprZipStream(std::ostream& stream) const
3923 stream << "Name of int array : \"" << _name << "\"\n";
3924 reprZipWithoutNameStream(stream);
3927 void DataArrayInt::reprNotTooLongStream(std::ostream& stream) const
3929 stream << "Name of int array : \"" << _name << "\"\n";
3930 reprNotTooLongWithoutNameStream(stream);
3933 void DataArrayInt::reprWithoutNameStream(std::ostream& stream) const
3935 DataArray::reprWithoutNameStream(stream);
3936 _mem.repr(getNumberOfComponents(),stream);
3939 void DataArrayInt::reprZipWithoutNameStream(std::ostream& stream) const
3941 DataArray::reprWithoutNameStream(stream);
3942 _mem.reprZip(getNumberOfComponents(),stream);
3945 void DataArrayInt::reprNotTooLongWithoutNameStream(std::ostream& stream) const
3947 DataArray::reprWithoutNameStream(stream);
3948 stream.precision(17);
3949 _mem.reprNotTooLong(getNumberOfComponents(),stream);
3952 void DataArrayInt::reprCppStream(const std::string& varName, std::ostream& stream) const
3954 int nbTuples=getNumberOfTuples(),nbComp=getNumberOfComponents();
3955 const int *data=getConstPointer();
3956 stream << "DataArrayInt *" << varName << "=DataArrayInt::New();" << std::endl;
3957 if(nbTuples*nbComp>=1)
3959 stream << "const int " << varName << "Data[" << nbTuples*nbComp << "]={";
3960 std::copy(data,data+nbTuples*nbComp-1,std::ostream_iterator<int>(stream,","));
3961 stream << data[nbTuples*nbComp-1] << "};" << std::endl;
3962 stream << varName << "->useArray(" << varName << "Data,false,CPP_DEALLOC," << nbTuples << "," << nbComp << ");" << std::endl;
3965 stream << varName << "->alloc(" << nbTuples << "," << nbComp << ");" << std::endl;
3966 stream << varName << "->setName(\"" << getName() << "\");" << std::endl;
3970 * Method that gives a quick overvien of \a this for python.
3972 void DataArrayInt::reprQuickOverview(std::ostream& stream) const
3974 static const std::size_t MAX_NB_OF_BYTE_IN_REPR=300;
3975 stream << "DataArrayInt C++ instance at " << this << ". ";
3978 int nbOfCompo=(int)_info_on_compo.size();
3981 int nbOfTuples=getNumberOfTuples();
3982 stream << "Number of tuples : " << nbOfTuples << ". Number of components : " << nbOfCompo << "." << std::endl;
3983 reprQuickOverviewData(stream,MAX_NB_OF_BYTE_IN_REPR);
3986 stream << "Number of components : 0.";
3989 stream << "*** No data allocated ****";
3992 void DataArrayInt::reprQuickOverviewData(std::ostream& stream, std::size_t maxNbOfByteInRepr) const
3994 const int *data=begin();
3995 int nbOfTuples=getNumberOfTuples();
3996 int nbOfCompo=(int)_info_on_compo.size();
3997 std::ostringstream oss2; oss2 << "[";
3998 std::string oss2Str(oss2.str());
3999 bool isFinished=true;
4000 for(int i=0;i<nbOfTuples && isFinished;i++)
4005 for(int j=0;j<nbOfCompo;j++,data++)
4008 if(j!=nbOfCompo-1) oss2 << ", ";
4014 if(i!=nbOfTuples-1) oss2 << ", ";
4015 std::string oss3Str(oss2.str());
4016 if(oss3Str.length()<maxNbOfByteInRepr)
4028 * Modifies in place \a this one-dimensional array so that each value \a v = \a indArrBg[ \a v ],
4029 * i.e. a current value is used as in index to get a new value from \a indArrBg.
4030 * \param [in] indArrBg - pointer to the first element of array of new values to assign
4032 * \param [in] indArrEnd - specifies the end of the array \a indArrBg, so that
4033 * the last value of \a indArrBg is \a indArrEnd[ -1 ].
4034 * \throw If \a this->getNumberOfComponents() != 1
4035 * \throw If any value of \a this can't be used as a valid index for
4036 * [\a indArrBg, \a indArrEnd).
4040 void DataArrayInt::transformWithIndArr(const int *indArrBg, const int *indArrEnd)
4043 if(getNumberOfComponents()!=1)
4044 throw INTERP_KERNEL::Exception("Call transformWithIndArr method on DataArrayInt with only one component, you can call 'rearrange' method before !");
4045 int nbElemsIn((int)std::distance(indArrBg,indArrEnd)),nbOfTuples(getNumberOfTuples()),*pt(getPointer());
4046 for(int i=0;i<nbOfTuples;i++,pt++)
4048 if(*pt>=0 && *pt<nbElemsIn)
4052 std::ostringstream oss; oss << "DataArrayInt::transformWithIndArr : error on tuple #" << i << " of this value is " << *pt << ", should be in [0," << nbElemsIn << ") !";
4053 throw INTERP_KERNEL::Exception(oss.str().c_str());
4060 * Computes distribution of values of \a this one-dimensional array between given value
4061 * ranges (casts). This method is typically useful for entity number spliting by types,
4063 * \warning The values contained in \a arrBg should be sorted ascendently. No
4064 * check of this is be done. If not, the result is not warranted.
4065 * \param [in] arrBg - the array of ascending values defining the value ranges. The i-th
4066 * value of \a arrBg (\a arrBg[ i ]) gives the lowest value of the i-th range,
4067 * and the greatest value of the i-th range equals to \a arrBg[ i+1 ] - 1. \a
4068 * arrBg containing \a n values defines \a n-1 ranges. The last value of \a arrBg
4069 * should be more than every value in \a this array.
4070 * \param [in] arrEnd - specifies the end of the array \a arrBg, so that
4071 * the last value of \a arrBg is \a arrEnd[ -1 ].
4072 * \param [out] castArr - a new instance of DataArrayInt, of same size as \a this array
4073 * (same number of tuples and components), the caller is to delete
4074 * using decrRef() as it is no more needed.
4075 * This array contains indices of ranges for every value of \a this array. I.e.
4076 * the i-th value of \a castArr gives the index of range the i-th value of \a this
4077 * belongs to. Or, in other words, this parameter contains for each tuple in \a
4078 * this in which cast it holds.
4079 * \param [out] rankInsideCast - a new instance of DataArrayInt, of same size as \a this
4080 * array, the caller is to delete using decrRef() as it is no more needed.
4081 * This array contains ranks of values of \a this array within ranges
4082 * they belongs to. I.e. the i-th value of \a rankInsideCast gives the rank of
4083 * the i-th value of \a this array within the \a castArr[ i ]-th range, to which
4084 * the i-th value of \a this belongs to. Or, in other words, this param contains
4085 * for each tuple its rank inside its cast. The rank is computed as difference
4086 * between the value and the lowest value of range.
4087 * \param [out] castsPresent - a new instance of DataArrayInt, containing indices of
4088 * ranges (casts) to which at least one value of \a this array belongs.
4089 * Or, in other words, this param contains the casts that \a this contains.
4090 * The caller is to delete this array using decrRef() as it is no more needed.
4092 * \b Example: If \a this contains [6,5,0,3,2,7,8,1,4] and \a arrBg contains [0,4,9] then
4093 * the output of this method will be :
4094 * - \a castArr : [1,1,0,0,0,1,1,0,1]
4095 * - \a rankInsideCast: [2,1,0,3,2,3,4,1,0]
4096 * - \a castsPresent : [0,1]
4098 * I.e. values of \a this array belong to 2 ranges: #0 and #1. Value 6 belongs to the
4099 * range #1 and its rank within this range is 2; etc.
4101 * \throw If \a this->getNumberOfComponents() != 1.
4102 * \throw If \a arrEnd - arrBg < 2.
4103 * \throw If any value of \a this is not less than \a arrEnd[-1].
4105 void DataArrayInt::splitByValueRange(const int *arrBg, const int *arrEnd,
4106 DataArrayInt *& castArr, DataArrayInt *& rankInsideCast, DataArrayInt *& castsPresent) const
4109 if(getNumberOfComponents()!=1)
4110 throw INTERP_KERNEL::Exception("Call splitByValueRange method on DataArrayInt with only one component, you can call 'rearrange' method before !");
4111 int nbOfTuples=getNumberOfTuples();
4112 std::size_t nbOfCast=std::distance(arrBg,arrEnd);
4114 throw INTERP_KERNEL::Exception("DataArrayInt::splitByValueRange : The input array giving the cast range values should be of size >=2 !");
4116 const int *work=getConstPointer();
4117 typedef std::reverse_iterator<const int *> rintstart;
4118 rintstart bg(arrEnd);//OK no problem because size of 'arr' is greater or equal 2
4119 rintstart end2(arrBg);
4120 MCAuto<DataArrayInt> ret1=DataArrayInt::New();
4121 MCAuto<DataArrayInt> ret2=DataArrayInt::New();
4122 MCAuto<DataArrayInt> ret3=DataArrayInt::New();
4123 ret1->alloc(nbOfTuples,1);
4124 ret2->alloc(nbOfTuples,1);
4125 int *ret1Ptr=ret1->getPointer();
4126 int *ret2Ptr=ret2->getPointer();
4127 std::set<std::size_t> castsDetected;
4128 for(int i=0;i<nbOfTuples;i++)
4130 rintstart res=std::find_if(bg,end2,std::bind2nd(std::less_equal<int>(), work[i]));
4131 std::size_t pos=std::distance(bg,res);
4132 std::size_t pos2=nbOfCast-pos;
4135 ret1Ptr[i]=(int)pos2;
4136 ret2Ptr[i]=work[i]-arrBg[pos2];
4137 castsDetected.insert(pos2);
4141 std::ostringstream oss; oss << "DataArrayInt::splitByValueRange : At rank #" << i << " the value is " << work[i] << " should be in [0," << *bg << ") !";
4142 throw INTERP_KERNEL::Exception(oss.str().c_str());
4145 ret3->alloc((int)castsDetected.size(),1);
4146 std::copy(castsDetected.begin(),castsDetected.end(),ret3->getPointer());
4147 castArr=ret1.retn();
4148 rankInsideCast=ret2.retn();
4149 castsPresent=ret3.retn();
4153 * This method look at \a this if it can be considered as a range defined by the 3-tuple ( \a strt , \a sttoopp , \a stteepp ).
4154 * If false is returned the tuple must be ignored. If true is returned \a this can be considered by a range( \a strt , \a sttoopp , \a stteepp ).
4155 * This method works only if \a this is allocated and single component. If not an exception will be thrown.
4157 * \param [out] strt - the start of the range (included) if true is returned.
4158 * \param [out] sttoopp - the end of the range (not included) if true is returned.
4159 * \param [out] stteepp - the step of the range if true is returned.
4160 * \return the verdict of the check.
4162 * \sa DataArray::GetNumberOfItemGivenBES
4164 bool DataArrayInt::isRange(int& strt, int& sttoopp, int& stteepp) const
4167 if(getNumberOfComponents()!=1)
4168 throw INTERP_KERNEL::Exception("DataArrayInt::isRange : this must be single component array !");
4169 int nbTuples(getNumberOfTuples());
4171 { strt=0; sttoopp=0; stteepp=1; return true; }
4172 const int *pt(begin());
4175 { sttoopp=strt+1; stteepp=1; return true; }
4176 strt=*pt; sttoopp=pt[nbTuples-1];
4182 int a(sttoopp-1-strt),tmp(strt);
4183 if(a%(nbTuples-1)!=0)
4185 stteepp=a/(nbTuples-1);
4186 for(int i=0;i<nbTuples;i++,tmp+=stteepp)
4194 int a(strt-sttoopp-1),tmp(strt);
4195 if(a%(nbTuples-1)!=0)
4197 stteepp=-(a/(nbTuples-1));
4198 for(int i=0;i<nbTuples;i++,tmp+=stteepp)
4206 * Creates a one-dimensional DataArrayInt (\a res) whose contents are computed from
4207 * values of \a this (\a a) and the given (\a indArr) arrays as follows:
4208 * \a res[ \a indArr[ \a a[ i ]]] = i. I.e. for each value in place i \a v = \a a[ i ],
4209 * new value in place \a indArr[ \a v ] is i.
4210 * \param [in] indArrBg - the array holding indices within the result array to assign
4211 * indices of values of \a this array pointing to values of \a indArrBg.
4212 * \param [in] indArrEnd - specifies the end of the array \a indArrBg, so that
4213 * the last value of \a indArrBg is \a indArrEnd[ -1 ].
4214 * \return DataArrayInt * - the new instance of DataArrayInt.
4215 * The caller is to delete this result array using decrRef() as it is no more
4217 * \throw If \a this->getNumberOfComponents() != 1.
4218 * \throw If any value of \a this array is not a valid index for \a indArrBg array.
4219 * \throw If any value of \a indArrBg is not a valid index for \a this array.
4221 DataArrayInt *DataArrayInt::transformWithIndArrR(const int *indArrBg, const int *indArrEnd) const
4224 if(getNumberOfComponents()!=1)
4225 throw INTERP_KERNEL::Exception("Call transformWithIndArrR method on DataArrayInt with only one component, you can call 'rearrange' method before !");
4226 int nbElemsIn=(int)std::distance(indArrBg,indArrEnd);
4227 int nbOfTuples=getNumberOfTuples();
4228 const int *pt=getConstPointer();
4229 MCAuto<DataArrayInt> ret=DataArrayInt::New();
4230 ret->alloc(nbOfTuples,1);
4231 ret->fillWithValue(-1);
4232 int *tmp=ret->getPointer();
4233 for(int i=0;i<nbOfTuples;i++,pt++)
4235 if(*pt>=0 && *pt<nbElemsIn)
4237 int pos=indArrBg[*pt];
4238 if(pos>=0 && pos<nbOfTuples)
4242 std::ostringstream oss; oss << "DataArrayInt::transformWithIndArrR : error on tuple #" << i << " value of new pos is " << pos << " ( indArrBg[" << *pt << "]) ! Should be in [0," << nbOfTuples << ") !";
4243 throw INTERP_KERNEL::Exception(oss.str().c_str());
4248 std::ostringstream oss; oss << "DataArrayInt::transformWithIndArrR : error on tuple #" << i << " value is " << *pt << " and indirectionnal array as a size equal to " << nbElemsIn << " !";
4249 throw INTERP_KERNEL::Exception(oss.str().c_str());
4256 * Creates a one-dimensional DataArrayInt of given length, whose contents are computed
4257 * from values of \a this array, which is supposed to contain a renumbering map in
4258 * "Old to New" mode. The result array contains a renumbering map in "New to Old" mode.
4259 * To know how to use the renumbering maps see \ref numbering.
4260 * \param [in] newNbOfElem - the number of tuples in the result array.
4261 * \return DataArrayInt * - the new instance of DataArrayInt.
4262 * The caller is to delete this result array using decrRef() as it is no more
4265 * \if ENABLE_EXAMPLES
4266 * \ref cpp_mcdataarrayint_invertarrayo2n2n2o "Here is a C++ example".<br>
4267 * \ref py_mcdataarrayint_invertarrayo2n2n2o "Here is a Python example".
4270 DataArrayInt *DataArrayInt::invertArrayO2N2N2O(int newNbOfElem) const
4272 MCAuto<DataArrayInt> ret=DataArrayInt::New();
4273 ret->alloc(newNbOfElem,1);
4274 int nbOfOldNodes=getNumberOfTuples();
4275 const int *old2New=getConstPointer();
4276 int *pt=ret->getPointer();
4277 for(int i=0;i!=nbOfOldNodes;i++)
4279 int newp(old2New[i]);
4282 if(newp>=0 && newp<newNbOfElem)
4286 std::ostringstream oss; oss << "DataArrayInt::invertArrayO2N2N2O : At place #" << i << " the newplace is " << newp << " must be in [0," << newNbOfElem << ") !";
4287 throw INTERP_KERNEL::Exception(oss.str().c_str());
4295 * This method is similar to DataArrayInt::invertArrayO2N2N2O except that
4296 * Example : If \a this contains [0,1,2,0,3,4,5,4,6,4] this method will return [0,1,2,4,5,6,8] whereas DataArrayInt::invertArrayO2N2N2O returns [3,1,2,4,9,6,8]
4298 DataArrayInt *DataArrayInt::invertArrayO2N2N2OBis(int newNbOfElem) const
4300 MCAuto<DataArrayInt> ret=DataArrayInt::New();
4301 ret->alloc(newNbOfElem,1);
4302 int nbOfOldNodes=getNumberOfTuples();
4303 const int *old2New=getConstPointer();
4304 int *pt=ret->getPointer();
4305 for(int i=nbOfOldNodes-1;i>=0;i--)
4307 int newp(old2New[i]);
4310 if(newp>=0 && newp<newNbOfElem)
4314 std::ostringstream oss; oss << "DataArrayInt::invertArrayO2N2N2OBis : At place #" << i << " the newplace is " << newp << " must be in [0," << newNbOfElem << ") !";
4315 throw INTERP_KERNEL::Exception(oss.str().c_str());
4323 * Creates a one-dimensional DataArrayInt of given length, whose contents are computed
4324 * from values of \a this array, which is supposed to contain a renumbering map in
4325 * "New to Old" mode. The result array contains a renumbering map in "Old to New" mode.
4326 * To know how to use the renumbering maps see \ref numbering.
4327 * \param [in] newNbOfElem - the number of tuples in the result array.
4328 * \return DataArrayInt * - the new instance of DataArrayInt.
4329 * The caller is to delete this result array using decrRef() as it is no more
4332 * \if ENABLE_EXAMPLES
4333 * \ref cpp_mcdataarrayint_invertarrayn2o2o2n "Here is a C++ example".
4335 * \ref py_mcdataarrayint_invertarrayn2o2o2n "Here is a Python example".
4338 DataArrayInt *DataArrayInt::invertArrayN2O2O2N(int oldNbOfElem) const
4341 MCAuto<DataArrayInt> ret=DataArrayInt::New();
4342 ret->alloc(oldNbOfElem,1);
4343 const int *new2Old=getConstPointer();
4344 int *pt=ret->getPointer();
4345 std::fill(pt,pt+oldNbOfElem,-1);
4346 int nbOfNewElems=getNumberOfTuples();
4347 for(int i=0;i<nbOfNewElems;i++)
4350 if(v>=0 && v<oldNbOfElem)
4354 std::ostringstream oss; oss << "DataArrayInt::invertArrayN2O2O2N : in new id #" << i << " old value is " << v << " expected to be in [0," << oldNbOfElem << ") !";
4355 throw INTERP_KERNEL::Exception(oss.str().c_str());
4362 * Equivalent to DataArrayInt::isEqual except that if false the reason of
4363 * mismatch is given.
4365 * \param [in] other the instance to be compared with \a this
4366 * \param [out] reason In case of inequality returns the reason.
4367 * \sa DataArrayInt::isEqual
4369 bool DataArrayInt::isEqualIfNotWhy(const DataArrayInt& other, std::string& reason) const
4371 if(!areInfoEqualsIfNotWhy(other,reason))
4373 return _mem.isEqual(other._mem,0,reason);
4377 * Checks if \a this and another DataArrayInt are fully equal. For more info see
4378 * \ref MEDCouplingArrayBasicsCompare.
4379 * \param [in] other - an instance of DataArrayInt to compare with \a this one.
4380 * \return bool - \a true if the two arrays are equal, \a false else.
4382 bool DataArrayInt::isEqual(const DataArrayInt& other) const
4385 return isEqualIfNotWhy(other,tmp);
4389 * Checks if values of \a this and another DataArrayInt are equal. For more info see
4390 * \ref MEDCouplingArrayBasicsCompare.
4391 * \param [in] other - an instance of DataArrayInt to compare with \a this one.
4392 * \return bool - \a true if the values of two arrays are equal, \a false else.
4394 bool DataArrayInt::isEqualWithoutConsideringStr(const DataArrayInt& other) const
4397 return _mem.isEqual(other._mem,0,tmp);
4401 * Checks if values of \a this and another DataArrayInt are equal. Comparison is
4402 * performed on sorted value sequences.
4403 * For more info see\ref MEDCouplingArrayBasicsCompare.
4404 * \param [in] other - an instance of DataArrayInt to compare with \a this one.
4405 * \return bool - \a true if the sorted values of two arrays are equal, \a false else.
4407 bool DataArrayInt::isEqualWithoutConsideringStrAndOrder(const DataArrayInt& other) const
4409 MCAuto<DataArrayInt> a=deepCopy();
4410 MCAuto<DataArrayInt> b=other.deepCopy();
4413 return a->isEqualWithoutConsideringStr(*b);
4417 * This method compares content of input vector \a v and \a this.
4418 * If for each id in \a this v[id]==True and for all other ids id2 not in \a this v[id2]==False, true is returned.
4419 * For performance reasons \a this is expected to be sorted ascendingly. If not an exception will be thrown.
4421 * \param [in] v - the vector of 'flags' to be compared with \a this.
4423 * \throw If \a this is not sorted ascendingly.
4424 * \throw If \a this has not exactly one component.
4425 * \throw If \a this is not allocated.
4427 bool DataArrayInt::isFittingWith(const std::vector<bool>& v) const
4430 if(getNumberOfComponents()!=1)
4431 throw INTERP_KERNEL::Exception("DataArrayInt::isFittingWith : number of components of this should be equal to one !");
4432 const int *w(begin()),*end2(end());
4433 int refVal=-std::numeric_limits<int>::max();
4435 std::vector<bool>::const_iterator it(v.begin());
4436 for(;it!=v.end();it++,i++)
4448 std::ostringstream oss; oss << "DataArrayInt::isFittingWith : At pos #" << std::distance(begin(),w-1) << " this is not sorted ascendingly !";
4449 throw INTERP_KERNEL::Exception(oss.str().c_str());
4463 * This method assumes that \a this has one component and is allocated. This method scans all tuples in \a this and for all tuple equal to \a val
4464 * put True to the corresponding entry in \a vec.
4465 * \a vec is expected to be with the same size than the number of tuples of \a this.
4467 * \sa DataArrayInt::switchOnTupleNotEqualTo.
4469 void DataArrayInt::switchOnTupleEqualTo(int val, std::vector<bool>& vec) const
4472 if(getNumberOfComponents()!=1)
4473 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleEqualTo : number of components of this should be equal to one !");
4474 int nbOfTuples(getNumberOfTuples());
4475 if(nbOfTuples!=(int)vec.size())
4476 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleEqualTo : number of tuples of this should be equal to size of input vector of bool !");
4477 const int *pt(begin());
4478 for(int i=0;i<nbOfTuples;i++)
4484 * This method assumes that \a this has one component and is allocated. This method scans all tuples in \a this and for all tuple different from \a val
4485 * put True to the corresponding entry in \a vec.
4486 * \a vec is expected to be with the same size than the number of tuples of \a this.
4488 * \sa DataArrayInt::switchOnTupleEqualTo.
4490 void DataArrayInt::switchOnTupleNotEqualTo(int val, std::vector<bool>& vec) const
4493 if(getNumberOfComponents()!=1)
4494 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleNotEqualTo : number of components of this should be equal to one !");
4495 int nbOfTuples(getNumberOfTuples());
4496 if(nbOfTuples!=(int)vec.size())
4497 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleNotEqualTo : number of tuples of this should be equal to size of input vector of bool !");
4498 const int *pt(begin());
4499 for(int i=0;i<nbOfTuples;i++)
4505 * Computes for each tuple the sum of number of components values in the tuple and return it.
4507 * \return DataArrayInt * - the new instance of DataArrayInt containing the
4508 * same number of tuples as \a this array and one component.
4509 * The caller is to delete this result array using decrRef() as it is no more
4511 * \throw If \a this is not allocated.
4513 DataArrayInt *DataArrayInt::sumPerTuple() const
4516 int nbOfComp(getNumberOfComponents()),nbOfTuple(getNumberOfTuples());
4517 MCAuto<DataArrayInt> ret(DataArrayInt::New());
4518 ret->alloc(nbOfTuple,1);
4519 const int *src(getConstPointer());
4520 int *dest(ret->getPointer());
4521 for(int i=0;i<nbOfTuple;i++,dest++,src+=nbOfComp)
4522 *dest=std::accumulate(src,src+nbOfComp,0);
4527 * Checks that \a this array is consistently **increasing** or **decreasing** in value.
4528 * If not an exception is thrown.
4529 * \param [in] increasing - if \a true, the array values should be increasing.
4530 * \throw If sequence of values is not strictly monotonic in agreement with \a
4532 * \throw If \a this->getNumberOfComponents() != 1.
4533 * \throw If \a this is not allocated.
4535 void DataArrayInt::checkMonotonic(bool increasing) const
4537 if(!isMonotonic(increasing))
4540 throw INTERP_KERNEL::Exception("DataArrayInt::checkMonotonic : 'this' is not INCREASING monotonic !");
4542 throw INTERP_KERNEL::Exception("DataArrayInt::checkMonotonic : 'this' is not DECREASING monotonic !");
4547 * Checks that \a this array is consistently **increasing** or **decreasing** in value.
4548 * \param [in] increasing - if \a true, array values should be increasing.
4549 * \return bool - \a true if values change in accordance with \a increasing arg.
4550 * \throw If \a this->getNumberOfComponents() != 1.
4551 * \throw If \a this is not allocated.
4553 bool DataArrayInt::isMonotonic(bool increasing) const
4556 if(getNumberOfComponents()!=1)
4557 throw INTERP_KERNEL::Exception("DataArrayInt::isMonotonic : only supported with 'this' array with ONE component !");
4558 int nbOfElements=getNumberOfTuples();
4559 const int *ptr=getConstPointer();
4565 for(int i=1;i<nbOfElements;i++)
4575 for(int i=1;i<nbOfElements;i++)
4587 * This method check that array consistently INCREASING or DECREASING in value.
4589 bool DataArrayInt::isStrictlyMonotonic(bool increasing) const
4592 if(getNumberOfComponents()!=1)
4593 throw INTERP_KERNEL::Exception("DataArrayInt::isStrictlyMonotonic : only supported with 'this' array with ONE component !");
4594 int nbOfElements=getNumberOfTuples();
4595 const int *ptr=getConstPointer();
4601 for(int i=1;i<nbOfElements;i++)
4611 for(int i=1;i<nbOfElements;i++)
4623 * This method check that array consistently INCREASING or DECREASING in value.
4625 void DataArrayInt::checkStrictlyMonotonic(bool increasing) const
4627 if(!isStrictlyMonotonic(increasing))
4630 throw INTERP_KERNEL::Exception("DataArrayInt::checkStrictlyMonotonic : 'this' is not strictly INCREASING monotonic !");
4632 throw INTERP_KERNEL::Exception("DataArrayInt::checkStrictlyMonotonic : 'this' is not strictly DECREASING monotonic !");
4637 * Creates a new one-dimensional DataArrayInt of the same size as \a this and a given
4638 * one-dimensional arrays that must be of the same length. The result array describes
4639 * correspondence between \a this and \a other arrays, so that
4640 * <em> other.getIJ(i,0) == this->getIJ(ret->getIJ(i),0)</em>. If such a permutation is
4641 * not possible because some element in \a other is not in \a this, an exception is thrown.
4642 * \param [in] other - an array to compute permutation to.
4643 * \return DataArrayInt * - a new instance of DataArrayInt, which is a permutation array
4644 * from \a this to \a other. The caller is to delete this array using decrRef() as it is
4646 * \throw If \a this->getNumberOfComponents() != 1.
4647 * \throw If \a other->getNumberOfComponents() != 1.
4648 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples().
4649 * \throw If \a other includes a value which is not in \a this array.
4651 * \if ENABLE_EXAMPLES
4652 * \ref cpp_mcdataarrayint_buildpermutationarr "Here is a C++ example".
4654 * \ref py_mcdataarrayint_buildpermutationarr "Here is a Python example".
4657 DataArrayInt *DataArrayInt::buildPermutationArr(const DataArrayInt& other) const
4660 if(getNumberOfComponents()!=1 || other.getNumberOfComponents()!=1)
4661 throw INTERP_KERNEL::Exception("DataArrayInt::buildPermutationArr : 'this' and 'other' have to have exactly ONE component !");
4662 int nbTuple=getNumberOfTuples();
4663 other.checkAllocated();
4664 if(nbTuple!=other.getNumberOfTuples())
4665 throw INTERP_KERNEL::Exception("DataArrayInt::buildPermutationArr : 'this' and 'other' must have the same number of tuple !");
4666 MCAuto<DataArrayInt> ret=DataArrayInt::New();
4667 ret->alloc(nbTuple,1);
4668 ret->fillWithValue(-1);
4669 const int *pt=getConstPointer();
4670 std::map<int,int> mm;
4671 for(int i=0;i<nbTuple;i++)
4673 pt=other.getConstPointer();
4674 int *retToFill=ret->getPointer();
4675 for(int i=0;i<nbTuple;i++)
4677 std::map<int,int>::const_iterator it=mm.find(pt[i]);
4680 std::ostringstream oss; oss << "DataArrayInt::buildPermutationArr : Arrays mismatch : element (" << pt[i] << ") in 'other' not findable in 'this' !";
4681 throw INTERP_KERNEL::Exception(oss.str().c_str());
4683 retToFill[i]=(*it).second;
4689 * Elements of \a partOfThis are expected to be included in \a this.
4690 * The returned array \a ret is so that this[ret]==partOfThis
4692 * For example, if \a this array contents are [9,10,0,6,4,11,3,8] and if \a partOfThis contains [6,0,11,8]
4693 * the return array will contain [3,2,5,7].
4695 * \a this is expected to be a 1 compo allocated array.
4696 * \param [in] partOfThis - A 1 compo allocated array
4697 * \return - A newly allocated array to be dealed by caller having the same number of tuples than \a partOfThis.
4698 * \throw if two same element is present twice in \a this
4699 * \throw if an element in \a partOfThis is \b NOT in \a this.
4701 DataArrayInt *DataArrayInt::indicesOfSubPart(const DataArrayInt& partOfThis) const
4703 if(getNumberOfComponents()!=1 || partOfThis.getNumberOfComponents()!=1)
4704 throw INTERP_KERNEL::Exception("DataArrayInt::indicesOfSubPart : this and input array must be one component array !");
4705 checkAllocated(); partOfThis.checkAllocated();
4706 int thisNbTuples(getNumberOfTuples()),nbTuples(partOfThis.getNumberOfTuples());
4707 const int *thisPt(begin()),*pt(partOfThis.begin());
4708 MCAuto<DataArrayInt> ret(DataArrayInt::New());
4709 ret->alloc(nbTuples,1);
4710 int *retPt(ret->getPointer());
4711 std::map<int,int> m;
4712 for(int i=0;i<thisNbTuples;i++,thisPt++)
4714 if(m.size()!=thisNbTuples)
4715 throw INTERP_KERNEL::Exception("DataArrayInt::indicesOfSubPart : some elements appears more than once !");
4716 for(int i=0;i<nbTuples;i++,retPt++,pt++)
4718 std::map<int,int>::const_iterator it(m.find(*pt));
4720 *retPt=(*it).second;
4723 std::ostringstream oss; oss << "DataArrayInt::indicesOfSubPart : At pos #" << i << " of input array value is " << *pt << " not in this !";
4724 throw INTERP_KERNEL::Exception(oss.str());
4731 * Returns a new DataArrayInt containing a renumbering map in "Old to New" mode.
4732 * This map, if applied to \a this array, would make it sorted. For example, if
4733 * \a this array contents are [9,10,0,6,4,11,3,7] then the contents of the result array
4734 * are [5,6,0,3,2,7,1,4]; if this result array (\a res) is used as an argument in call
4735 * \a this->renumber(\a res) then the returned array contains [0,3,4,6,7,9,10,11].
4736 * This method is useful for renumbering (in MED file for example). For more info
4737 * on renumbering see \ref numbering.
4738 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
4739 * array using decrRef() as it is no more needed.
4740 * \throw If \a this is not allocated.
4741 * \throw If \a this->getNumberOfComponents() != 1.
4742 * \throw If there are equal values in \a this array.
4744 DataArrayInt *DataArrayInt::checkAndPreparePermutation() const
4747 if(getNumberOfComponents()!=1)
4748 throw INTERP_KERNEL::Exception("DataArrayInt::checkAndPreparePermutation : number of components must == 1 !");
4749 int nbTuples=getNumberOfTuples();
4750 const int *pt=getConstPointer();
4751 int *pt2=CheckAndPreparePermutation(pt,pt+nbTuples);
4752 DataArrayInt *ret=DataArrayInt::New();
4753 ret->useArray(pt2,true,C_DEALLOC,nbTuples,1);
4758 * This method tries to find the permutation to apply to the first input \a ids1 to obtain the same array (without considering strings informations) the second
4759 * input array \a ids2.
4760 * \a ids1 and \a ids2 are expected to be both a list of ids (both with number of components equal to one) not sorted and with values that can be negative.
4761 * This method will throw an exception is no such permutation array can be obtained. It is typically the case if there is some ids in \a ids1 not in \a ids2 or
4763 * In case of success (no throw) : \c ids1->renumber(ret)->isEqual(ids2) where \a ret is the return of this method.
4765 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
4766 * array using decrRef() as it is no more needed.
4767 * \throw If either ids1 or ids2 is null not allocated or not with one components.
4770 DataArrayInt *DataArrayInt::FindPermutationFromFirstToSecond(const DataArrayInt *ids1, const DataArrayInt *ids2)
4773 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two input arrays must be not null !");
4774 if(!ids1->isAllocated() || !ids2->isAllocated())
4775 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two input arrays must be allocated !");
4776 if(ids1->getNumberOfComponents()!=1 || ids2->getNumberOfComponents()!=1)
4777 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two input arrays have exactly one component !");
4778 if(ids1->getNumberOfTuples()!=ids2->getNumberOfTuples())
4780 std::ostringstream oss; oss << "DataArrayInt::FindPermutationFromFirstToSecond : first array has " << ids1->getNumberOfTuples() << " tuples and the second one " << ids2->getNumberOfTuples() << " tuples ! No chance to find a permutation between the 2 arrays !";
4781 throw INTERP_KERNEL::Exception(oss.str().c_str());
4783 MCAuto<DataArrayInt> p1(ids1->deepCopy());
4784 MCAuto<DataArrayInt> p2(ids2->deepCopy());
4785 p1->sort(true); p2->sort(true);
4786 if(!p1->isEqualWithoutConsideringStr(*p2))
4787 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two arrays are not lying on same ids ! Impossible to find a permutation between the 2 arrays !");
4788 p1=ids1->checkAndPreparePermutation();
4789 p2=ids2->checkAndPreparePermutation();
4790 p2=p2->invertArrayO2N2N2O(p2->getNumberOfTuples());
4791 p2=p2->selectByTupleIdSafe(p1->begin(),p1->end());
4796 * Returns two arrays describing a surjective mapping from \a this set of values (\a A)
4797 * onto a set of values of size \a targetNb (\a B). The surjective function is
4798 * \a B[ \a A[ i ]] = i. That is to say that for each \a id in [0,\a targetNb), where \a
4799 * targetNb < \a this->getNumberOfTuples(), there exists at least one tupleId (\a tid) so
4800 * that <em> this->getIJ( tid, 0 ) == id</em>. <br>
4801 * The first of out arrays returns indices of elements of \a this array, grouped by their
4802 * place in the set \a B. The second out array is the index of the first one; it shows how
4803 * many elements of \a A are mapped into each element of \a B. <br>
4805 * mapping and its usage in renumbering see \ref numbering. <br>
4807 * - \a this: [0,3,2,3,2,2,1,2]
4809 * - \a arr: [0, 6, 2,4,5,7, 1,3]
4810 * - \a arrI: [0,1,2,6,8]
4812 * This result means: <br>
4813 * the element of \a B 0 encounters within \a A once (\a arrI[ 0+1 ] - \a arrI[ 0 ]) and
4814 * its index within \a A is 0 ( \a arr[ 0:1 ] == \a arr[ \a arrI[ 0 ] : \a arrI[ 0+1 ]]);<br>
4815 * the element of \a B 2 encounters within \a A 4 times (\a arrI[ 2+1 ] - \a arrI[ 2 ]) and
4816 * its indices within \a A are [2,4,5,7] ( \a arr[ 2:6 ] == \a arr[ \a arrI[ 2 ] :
4817 * \a arrI[ 2+1 ]]); <br> etc.
4818 * \param [in] targetNb - the size of the set \a B. \a targetNb must be equal or more
4819 * than the maximal value of \a A.
4820 * \param [out] arr - a new instance of DataArrayInt returning indices of
4821 * elements of \a this, grouped by their place in the set \a B. The caller is to delete
4822 * this array using decrRef() as it is no more needed.
4823 * \param [out] arrI - a new instance of DataArrayInt returning size of groups of equal
4824 * elements of \a this. The caller is to delete this array using decrRef() as it
4825 * is no more needed.
4826 * \throw If \a this is not allocated.
4827 * \throw If \a this->getNumberOfComponents() != 1.
4828 * \throw If any value in \a this is more or equal to \a targetNb.
4830 void DataArrayInt::changeSurjectiveFormat(int targetNb, DataArrayInt *&arr, DataArrayInt *&arrI) const
4833 if(getNumberOfComponents()!=1)
4834 throw INTERP_KERNEL::Exception("DataArrayInt::changeSurjectiveFormat : number of components must == 1 !");
4835 int nbOfTuples=getNumberOfTuples();
4836 MCAuto<DataArrayInt> ret(DataArrayInt::New());
4837 MCAuto<DataArrayInt> retI(DataArrayInt::New());
4838 retI->alloc(targetNb+1,1);
4839 const int *input=getConstPointer();
4840 std::vector< std::vector<int> > tmp(targetNb);
4841 for(int i=0;i<nbOfTuples;i++)
4844 if(tmp2>=0 && tmp2<targetNb)
4845 tmp[tmp2].push_back(i);
4848 std::ostringstream oss; oss << "DataArrayInt::changeSurjectiveFormat : At pos " << i << " presence of element " << tmp2 << " ! should be in [0," << targetNb << ") !";
4849 throw INTERP_KERNEL::Exception(oss.str().c_str());
4852 int *retIPtr=retI->getPointer();
4854 for(std::vector< std::vector<int> >::const_iterator it1=tmp.begin();it1!=tmp.end();it1++,retIPtr++)
4855 retIPtr[1]=retIPtr[0]+(int)((*it1).size());
4856 if(nbOfTuples!=retI->getIJ(targetNb,0))
4857 throw INTERP_KERNEL::Exception("DataArrayInt::changeSurjectiveFormat : big problem should never happen !");
4858 ret->alloc(nbOfTuples,1);
4859 int *retPtr=ret->getPointer();
4860 for(std::vector< std::vector<int> >::const_iterator it1=tmp.begin();it1!=tmp.end();it1++)
4861 retPtr=std::copy((*it1).begin(),(*it1).end(),retPtr);
4868 * Returns a new DataArrayInt containing a renumbering map in "Old to New" mode computed
4869 * from a zip representation of a surjective format (returned e.g. by
4870 * \ref MEDCoupling::DataArrayDouble::findCommonTuples() "DataArrayDouble::findCommonTuples()"
4871 * for example). The result array minimizes the permutation. <br>
4872 * For more info on renumbering see \ref numbering. <br>
4874 * - \a nbOfOldTuples: 10
4875 * - \a arr : [0,3, 5,7,9]
4876 * - \a arrIBg : [0,2,5]
4877 * - \a newNbOfTuples: 7
4878 * - result array : [0,1,2,0,3,4,5,4,6,4]
4880 * \param [in] nbOfOldTuples - number of tuples in the initial array \a arr.
4881 * \param [in] arr - the array of tuple indices grouped by \a arrIBg array.
4882 * \param [in] arrIBg - the array dividing all indices stored in \a arr into groups of
4883 * (indices of) equal values. Its every element (except the last one) points to
4884 * the first element of a group of equal values.
4885 * \param [in] arrIEnd - specifies the end of \a arrIBg, so that the last element of \a
4886 * arrIBg is \a arrIEnd[ -1 ].
4887 * \param [out] newNbOfTuples - number of tuples after surjection application.
4888 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
4889 * array using decrRef() as it is no more needed.
4890 * \throw If any value of \a arr breaks condition ( 0 <= \a arr[ i ] < \a nbOfOldTuples ).
4892 DataArrayInt *DataArrayInt::ConvertIndexArrayToO2N(int nbOfOldTuples, const int *arr, const int *arrIBg, const int *arrIEnd, int &newNbOfTuples)
4894 MCAuto<DataArrayInt> ret=DataArrayInt::New();
4895 ret->alloc(nbOfOldTuples,1);
4896 int *pt=ret->getPointer();
4897 std::fill(pt,pt+nbOfOldTuples,-1);
4898 int nbOfGrps=((int)std::distance(arrIBg,arrIEnd))-1;
4899 const int *cIPtr=arrIBg;
4900 for(int i=0;i<nbOfGrps;i++)
4901 pt[arr[cIPtr[i]]]=-(i+2);
4903 for(int iNode=0;iNode<nbOfOldTuples;iNode++)
4911 int grpId=-(pt[iNode]+2);
4912 for(int j=cIPtr[grpId];j<cIPtr[grpId+1];j++)
4914 if(arr[j]>=0 && arr[j]<nbOfOldTuples)
4918 std::ostringstream oss; oss << "DataArrayInt::ConvertIndexArrayToO2N : With element #" << j << " value is " << arr[j] << " should be in [0," << nbOfOldTuples << ") !";
4919 throw INTERP_KERNEL::Exception(oss.str().c_str());
4926 newNbOfTuples=newNb;
4931 * Returns a new DataArrayInt containing a renumbering map in "New to Old" mode,
4932 * which if applied to \a this array would make it sorted ascendingly.
4933 * For more info on renumbering see \ref numbering. <br>
4935 * - \a this: [2,0,1,1,0,1,2,0,1,1,0,0]
4936 * - result: [10,0,5,6,1,7,11,2,8,9,3,4]
4937 * - after applying result to \a this: [0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2]
4939 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
4940 * array using decrRef() as it is no more needed.
4941 * \throw If \a this is not allocated.
4942 * \throw If \a this->getNumberOfComponents() != 1.
4944 DataArrayInt *DataArrayInt::buildPermArrPerLevel() const
4947 if(getNumberOfComponents()!=1)
4948 throw INTERP_KERNEL::Exception("DataArrayInt::buildPermArrPerLevel : number of components must == 1 !");
4949 int nbOfTuples=getNumberOfTuples();
4950 const int *pt=getConstPointer();
4951 std::map<int,int> m;
4952 MCAuto<DataArrayInt> ret=DataArrayInt::New();
4953 ret->alloc(nbOfTuples,1);
4954 int *opt=ret->getPointer();
4955 for(int i=0;i<nbOfTuples;i++,pt++,opt++)
4958 std::map<int,int>::iterator it=m.find(val);
4967 m.insert(std::pair<int,int>(val,1));
4971 for(std::map<int,int>::iterator it=m.begin();it!=m.end();it++)
4973 int vt=(*it).second;
4977 pt=getConstPointer();
4978 opt=ret->getPointer();
4979 for(int i=0;i<nbOfTuples;i++,pt++,opt++)
4986 * Checks if \a this array has the given size, and if its contents is equal to an array filled with
4987 * iota(). This method is particularly useful for DataArrayInt instances that represent
4988 * a renumbering array, to check if there is a real need in renumbering.
4989 * This method checks than \a this can be considered as an identity mapping
4990 * of a set having \a sizeExpected elements into itself.
4992 * \param [in] sizeExpected - The number of elements expected.
4993 * \return bool - \a true if \a this array contents == \a range( \a this->getNumberOfTuples())
4994 * \throw If \a this is not allocated.
4995 * \throw If \a this->getNumberOfComponents() != 1.
4997 bool DataArrayInt::isIota(int sizeExpected) const
5000 if(getNumberOfComponents()!=1)
5002 int nbOfTuples(getNumberOfTuples());
5003 if(nbOfTuples!=sizeExpected)
5005 const int *pt=getConstPointer();
5006 for(int i=0;i<nbOfTuples;i++,pt++)
5013 * Checks if all values in \a this array are equal to \a val.
5014 * \param [in] val - value to check equality of array values to.
5015 * \return bool - \a true if all values are \a val.
5016 * \throw If \a this is not allocated.
5017 * \throw If \a this->getNumberOfComponents() != 1
5019 bool DataArrayInt::isUniform(int val) const
5022 if(getNumberOfComponents()!=1)
5023 throw INTERP_KERNEL::Exception("DataArrayInt::isUniform : must be applied on DataArrayInt with only one component, you can call 'rearrange' method before !");
5024 int nbOfTuples=getNumberOfTuples();
5025 const int *w=getConstPointer();
5026 const int *end2=w+nbOfTuples;
5034 * Checks if all values in \a this array are unique.
5035 * \return bool - \a true if condition above is true
5036 * \throw If \a this is not allocated.
5037 * \throw If \a this->getNumberOfComponents() != 1
5039 bool DataArrayInt::hasUniqueValues() const
5042 if(getNumberOfComponents()!=1)
5043 throw INTERP_KERNEL::Exception("DataArrayInt::hasOnlyUniqueValues: must be applied on DataArrayInt with only one component, you can call 'rearrange' method before !");
5044 int nbOfTuples(getNumberOfTuples());
5045 std::set<int> s(begin(),end()); // in C++11, should use unordered_set (O(1) complexity)
5046 if (s.size() != nbOfTuples)
5052 * Copy all components in a specified order from another DataArrayInt.
5053 * The specified components become the first ones in \a this array.
5054 * Both numerical and textual data is copied. The number of tuples in \a this and
5055 * the other array can be different.
5056 * \param [in] a - the array to copy data from.
5057 * \param [in] compoIds - sequence of zero based indices of components, data of which is
5059 * \throw If \a a is NULL.
5060 * \throw If \a compoIds.size() != \a a->getNumberOfComponents().
5061 * \throw If \a compoIds[i] < 0 or \a compoIds[i] > \a this->getNumberOfComponents().
5063 * \if ENABLE_EXAMPLES
5064 * \ref py_mcdataarrayint_setselectedcomponents "Here is a Python example".
5067 void DataArrayInt::setSelectedComponents(const DataArrayInt *a, const std::vector<int>& compoIds)
5070 throw INTERP_KERNEL::Exception("DataArrayInt::setSelectedComponents : input DataArrayInt is NULL !");
5072 a->checkAllocated();
5073 copyPartOfStringInfoFrom2(compoIds,*a);
5074 std::size_t partOfCompoSz=compoIds.size();
5075 int nbOfCompo=getNumberOfComponents();
5076 int nbOfTuples=std::min(getNumberOfTuples(),a->getNumberOfTuples());
5077 const int *ac=a->getConstPointer();
5078 int *nc=getPointer();
5079 for(int i=0;i<nbOfTuples;i++)
5080 for(std::size_t j=0;j<partOfCompoSz;j++,ac++)
5081 nc[nbOfCompo*i+compoIds[j]]=*ac;
5084 DataArrayIntIterator *DataArrayInt::iterator()
5086 return new DataArrayIntIterator(this);
5090 * Creates a new DataArrayInt containing IDs (indices) of tuples holding value equal to a
5091 * given one. The ids are sorted in the ascending order.
5092 * \param [in] val - the value to find within \a this.
5093 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5094 * array using decrRef() as it is no more needed.
5095 * \throw If \a this is not allocated.
5096 * \throw If \a this->getNumberOfComponents() != 1.
5097 * \sa DataArrayInt::findIdsEqualTuple
5099 DataArrayInt *DataArrayInt::findIdsEqual(int val) const
5102 if(getNumberOfComponents()!=1)
5103 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsEqual : the array must have only one component, you can call 'rearrange' method before !");
5104 const int *cptr(getConstPointer());
5105 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
5106 int nbOfTuples=getNumberOfTuples();
5107 for(int i=0;i<nbOfTuples;i++,cptr++)
5109 ret->pushBackSilent(i);
5114 * Creates a new DataArrayInt containing IDs (indices) of tuples holding value \b not
5115 * equal to a given one.
5116 * \param [in] val - the value to ignore within \a this.
5117 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5118 * array using decrRef() as it is no more needed.
5119 * \throw If \a this is not allocated.
5120 * \throw If \a this->getNumberOfComponents() != 1.
5122 DataArrayInt *DataArrayInt::findIdsNotEqual(int val) const
5125 if(getNumberOfComponents()!=1)
5126 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsNotEqual : the array must have only one component, you can call 'rearrange' method before !");
5127 const int *cptr(getConstPointer());
5128 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
5129 int nbOfTuples=getNumberOfTuples();
5130 for(int i=0;i<nbOfTuples;i++,cptr++)
5132 ret->pushBackSilent(i);
5137 * Creates a new DataArrayInt containing IDs (indices) of tuples holding tuple equal to those defined by [ \a tupleBg , \a tupleEnd )
5138 * This method is an extension of DataArrayInt::findIdsEqual method.
5140 * \param [in] tupleBg - the begin (included) of the input tuple to find within \a this.
5141 * \param [in] tupleEnd - the end (excluded) of the input tuple to find within \a this.
5142 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5143 * array using decrRef() as it is no more needed.
5144 * \throw If \a this is not allocated.
5145 * \throw If \a this->getNumberOfComponents() != std::distance(tupleBg,tupleEnd).
5146 * \throw If \a this->getNumberOfComponents() is equal to 0.
5147 * \sa DataArrayInt::findIdsEqual
5149 DataArrayInt *DataArrayInt::findIdsEqualTuple(const int *tupleBg, const int *tupleEnd) const
5151 std::size_t nbOfCompoExp(std::distance(tupleBg,tupleEnd));
5153 if(getNumberOfComponents()!=(int)nbOfCompoExp)
5155 std::ostringstream oss; oss << "DataArrayInt::findIdsEqualTuple : mismatch of number of components. Input tuple has " << nbOfCompoExp << " whereas this array has " << getNumberOfComponents() << " components !";
5156 throw INTERP_KERNEL::Exception(oss.str().c_str());
5159 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsEqualTuple : number of components should be > 0 !");
5160 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
5161 const int *bg(begin()),*end2(end()),*work(begin());
5164 work=std::search(work,end2,tupleBg,tupleEnd);
5167 std::size_t pos(std::distance(bg,work));
5168 if(pos%nbOfCompoExp==0)
5169 ret->pushBackSilent(pos/nbOfCompoExp);
5177 * Assigns \a newValue to all elements holding \a oldValue within \a this
5178 * one-dimensional array.
5179 * \param [in] oldValue - the value to replace.
5180 * \param [in] newValue - the value to assign.
5181 * \return int - number of replacements performed.
5182 * \throw If \a this is not allocated.
5183 * \throw If \a this->getNumberOfComponents() != 1.
5185 int DataArrayInt::changeValue(int oldValue, int newValue)
5188 if(getNumberOfComponents()!=1)
5189 throw INTERP_KERNEL::Exception("DataArrayInt::changeValue : the array must have only one component, you can call 'rearrange' method before !");
5190 if(oldValue==newValue)
5192 int *start(getPointer()),*end2(start+getNbOfElems());
5194 for(int *val=start;val!=end2;val++)
5208 * Creates a new DataArrayInt containing IDs (indices) of tuples holding value equal to
5209 * one of given values.
5210 * \param [in] valsBg - an array of values to find within \a this array.
5211 * \param [in] valsEnd - specifies the end of the array \a valsBg, so that
5212 * the last value of \a valsBg is \a valsEnd[ -1 ].
5213 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5214 * array using decrRef() as it is no more needed.
5215 * \throw If \a this->getNumberOfComponents() != 1.
5217 DataArrayInt *DataArrayInt::findIdsEqualList(const int *valsBg, const int *valsEnd) const
5219 if(getNumberOfComponents()!=1)
5220 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsEqualList : the array must have only one component, you can call 'rearrange' method before !");
5221 std::set<int> vals2(valsBg,valsEnd);
5222 const int *cptr(getConstPointer());
5223 std::vector<int> res;
5224 int nbOfTuples(getNumberOfTuples());
5225 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
5226 for(int i=0;i<nbOfTuples;i++,cptr++)
5227 if(vals2.find(*cptr)!=vals2.end())
5228 ret->pushBackSilent(i);
5233 * Creates a new DataArrayInt containing IDs (indices) of tuples holding values \b not
5234 * equal to any of given values.
5235 * \param [in] valsBg - an array of values to ignore within \a this array.
5236 * \param [in] valsEnd - specifies the end of the array \a valsBg, so that
5237 * the last value of \a valsBg is \a valsEnd[ -1 ].
5238 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5239 * array using decrRef() as it is no more needed.
5240 * \throw If \a this->getNumberOfComponents() != 1.
5242 DataArrayInt *DataArrayInt::findIdsNotEqualList(const int *valsBg, const int *valsEnd) const
5244 if(getNumberOfComponents()!=1)
5245 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsNotEqualList : the array must have only one component, you can call 'rearrange' method before !");
5246 std::set<int> vals2(valsBg,valsEnd);
5247 const int *cptr=getConstPointer();
5248 std::vector<int> res;
5249 int nbOfTuples=getNumberOfTuples();
5250 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
5251 for(int i=0;i<nbOfTuples;i++,cptr++)
5252 if(vals2.find(*cptr)==vals2.end())
5253 ret->pushBackSilent(i);
5258 * This method is an extension of DataArrayInt::findIdFirstEqual method because this method works for DataArrayInt with
5259 * any number of components excepted 0 (an INTERP_KERNEL::Exception is thrown in this case).
5260 * This method searches in \b this is there is a tuple that matched the input parameter \b tupl.
5261 * If any the tuple id is returned. If not -1 is returned.
5263 * This method throws an INTERP_KERNEL::Exception if the number of components in \b this mismatches with the size of
5264 * the input vector. An INTERP_KERNEL::Exception is thrown too if \b this is not allocated.
5266 * \return tuple id where \b tupl is. -1 if no such tuple exists in \b this.
5267 * \sa DataArrayInt::findIdSequence, DataArrayInt::presenceOfTuple.
5269 int DataArrayInt::findIdFirstEqualTuple(const std::vector<int>& tupl) const
5272 int nbOfCompo=getNumberOfComponents();
5274 throw INTERP_KERNEL::Exception("DataArrayInt::findIdFirstEqualTuple : 0 components in 'this' !");
5275 if(nbOfCompo!=(int)tupl.size())
5277 std::ostringstream oss; oss << "DataArrayInt::findIdFirstEqualTuple : 'this' contains " << nbOfCompo << " components and searching for a tuple of length " << tupl.size() << " !";
5278 throw INTERP_KERNEL::Exception(oss.str().c_str());
5280 const int *cptr=getConstPointer();
5281 std::size_t nbOfVals=getNbOfElems();
5282 for(const int *work=cptr;work!=cptr+nbOfVals;)
5284 work=std::search(work,cptr+nbOfVals,tupl.begin(),tupl.end());
5285 if(work!=cptr+nbOfVals)
5287 if(std::distance(cptr,work)%nbOfCompo!=0)
5290 return std::distance(cptr,work)/nbOfCompo;
5297 * This method searches the sequence specified in input parameter \b vals in \b this.
5298 * This works only for DataArrayInt having number of components equal to one (if not an INTERP_KERNEL::Exception will be thrown).
5299 * This method differs from DataArrayInt::findIdFirstEqualTuple in that the position is internal raw data is not considered here contrary to DataArrayInt::findIdFirstEqualTuple.
5300 * \sa DataArrayInt::findIdFirstEqualTuple
5302 int DataArrayInt::findIdSequence(const std::vector<int>& vals) const
5305 int nbOfCompo=getNumberOfComponents();
5307 throw INTERP_KERNEL::Exception("DataArrayInt::findIdSequence : works only for DataArrayInt instance with one component !");
5308 const int *cptr=getConstPointer();
5309 std::size_t nbOfVals=getNbOfElems();
5310 const int *loc=std::search(cptr,cptr+nbOfVals,vals.begin(),vals.end());
5311 if(loc!=cptr+nbOfVals)
5312 return std::distance(cptr,loc);
5317 * This method expects to be called when number of components of this is equal to one.
5318 * This method returns the tuple id, if it exists, of the first tuple equal to \b value.
5319 * If not any tuple contains \b value -1 is returned.
5320 * \sa DataArrayInt::presenceOfValue
5322 int DataArrayInt::findIdFirstEqual(int value) const
5325 if(getNumberOfComponents()!=1)
5326 throw INTERP_KERNEL::Exception("DataArrayInt::presenceOfValue : the array must have only one component, you can call 'rearrange' method before !");
5327 const int *cptr=getConstPointer();
5328 int nbOfTuples=getNumberOfTuples();
5329 const int *ret=std::find(cptr,cptr+nbOfTuples,value);
5330 if(ret!=cptr+nbOfTuples)
5331 return std::distance(cptr,ret);
5336 * This method expects to be called when number of components of this is equal to one.
5337 * This method returns the tuple id, if it exists, of the first tuple so that the value is contained in \b vals.
5338 * If not any tuple contains one of the values contained in 'vals' -1 is returned.
5339 * \sa DataArrayInt::presenceOfValue
5341 int DataArrayInt::findIdFirstEqual(const std::vector<int>& vals) const
5344 if(getNumberOfComponents()!=1)
5345 throw INTERP_KERNEL::Exception("DataArrayInt::presenceOfValue : the array must have only one component, you can call 'rearrange' method before !");
5346 std::set<int> vals2(vals.begin(),vals.end());
5347 const int *cptr=getConstPointer();
5348 int nbOfTuples=getNumberOfTuples();
5349 for(const int *w=cptr;w!=cptr+nbOfTuples;w++)
5350 if(vals2.find(*w)!=vals2.end())
5351 return std::distance(cptr,w);
5356 * This method returns the number of values in \a this that are equals to input parameter \a value.
5357 * This method only works for single component array.
5359 * \return a value in [ 0, \c this->getNumberOfTuples() )
5361 * \throw If \a this is not allocated
5364 int DataArrayInt::count(int value) const
5368 if(getNumberOfComponents()!=1)
5369 throw INTERP_KERNEL::Exception("DataArrayInt::count : must be applied on DataArrayInt with only one component, you can call 'rearrange' method before !");
5370 const int *vals=begin();
5371 int nbOfTuples=getNumberOfTuples();
5372 for(int i=0;i<nbOfTuples;i++,vals++)
5379 * This method is an extension of DataArrayInt::presenceOfValue method because this method works for DataArrayInt with
5380 * any number of components excepted 0 (an INTERP_KERNEL::Exception is thrown in this case).
5381 * This method searches in \b this is there is a tuple that matched the input parameter \b tupl.
5382 * This method throws an INTERP_KERNEL::Exception if the number of components in \b this mismatches with the size of
5383 * the input vector. An INTERP_KERNEL::Exception is thrown too if \b this is not allocated.
5384 * \sa DataArrayInt::findIdFirstEqualTuple
5386 bool DataArrayInt::presenceOfTuple(const std::vector<int>& tupl) const
5388 return findIdFirstEqualTuple(tupl)!=-1;
5393 * Returns \a true if a given value is present within \a this one-dimensional array.
5394 * \param [in] value - the value to find within \a this array.
5395 * \return bool - \a true in case if \a value is present within \a this array.
5396 * \throw If \a this is not allocated.
5397 * \throw If \a this->getNumberOfComponents() != 1.
5398 * \sa findIdFirstEqual()
5400 bool DataArrayInt::presenceOfValue(int value) const
5402 return findIdFirstEqual(value)!=-1;
5406 * This method expects to be called when number of components of this is equal to one.
5407 * This method returns true if it exists a tuple so that the value is contained in \b vals.
5408 * If not any tuple contains one of the values contained in 'vals' false is returned.
5409 * \sa DataArrayInt::findIdFirstEqual
5411 bool DataArrayInt::presenceOfValue(const std::vector<int>& vals) const
5413 return findIdFirstEqual(vals)!=-1;
5417 * Accumulates values of each component of \a this array.
5418 * \param [out] res - an array of length \a this->getNumberOfComponents(), allocated
5419 * by the caller, that is filled by this method with sum value for each
5421 * \throw If \a this is not allocated.
5423 void DataArrayInt::accumulate(int *res) const
5426 const int *ptr=getConstPointer();
5427 int nbTuple=getNumberOfTuples();
5428 int nbComps=getNumberOfComponents();
5429 std::fill(res,res+nbComps,0);
5430 for(int i=0;i<nbTuple;i++)
5431 std::transform(ptr+i*nbComps,ptr+(i+1)*nbComps,res,res,std::plus<int>());
5434 int DataArrayInt::accumulate(int compId) const
5437 const int *ptr=getConstPointer();
5438 int nbTuple=getNumberOfTuples();
5439 int nbComps=getNumberOfComponents();
5440 if(compId<0 || compId>=nbComps)
5441 throw INTERP_KERNEL::Exception("DataArrayInt::accumulate : Invalid compId specified : No such nb of components !");
5443 for(int i=0;i<nbTuple;i++)
5444 ret+=ptr[i*nbComps+compId];
5449 * This method accumulate using addition tuples in \a this using input index array [ \a bgOfIndex, \a endOfIndex ).
5450 * The returned array will have same number of components than \a this and number of tuples equal to
5451 * \c std::distance(bgOfIndex,endOfIndex) \b minus \b one.
5453 * The input index array is expected to be ascendingly sorted in which the all referenced ids should be in [0, \c this->getNumberOfTuples).
5455 * \param [in] bgOfIndex - begin (included) of the input index array.
5456 * \param [in] endOfIndex - end (excluded) of the input index array.
5457 * \return DataArrayInt * - the new instance having the same number of components than \a this.
5459 * \throw If bgOfIndex or end is NULL.
5460 * \throw If input index array is not ascendingly sorted.
5461 * \throw If there is an id in [ \a bgOfIndex, \a endOfIndex ) not in [0, \c this->getNumberOfTuples).
5462 * \throw If std::distance(bgOfIndex,endOfIndex)==0.
5464 DataArrayInt *DataArrayInt::accumulatePerChunck(const int *bgOfIndex, const int *endOfIndex) const
5466 if(!bgOfIndex || !endOfIndex)
5467 throw INTERP_KERNEL::Exception("DataArrayInt::accumulatePerChunck : input pointer NULL !");
5469 int nbCompo=getNumberOfComponents();
5470 int nbOfTuples=getNumberOfTuples();
5471 int sz=(int)std::distance(bgOfIndex,endOfIndex);
5473 throw INTERP_KERNEL::Exception("DataArrayInt::accumulatePerChunck : invalid size of input index array !");
5475 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(sz,nbCompo);
5476 const int *w=bgOfIndex;
5477 if(*w<0 || *w>=nbOfTuples)
5478 throw INTERP_KERNEL::Exception("DataArrayInt::accumulatePerChunck : The first element of the input index not in [0,nbOfTuples) !");
5479 const int *srcPt=begin()+(*w)*nbCompo;
5480 int *tmp=ret->getPointer();
5481 for(int i=0;i<sz;i++,tmp+=nbCompo,w++)
5483 std::fill(tmp,tmp+nbCompo,0);
5486 for(int j=w[0];j<w[1];j++,srcPt+=nbCompo)
5488 if(j>=0 && j<nbOfTuples)
5489 std::transform(srcPt,srcPt+nbCompo,tmp,tmp,std::plus<int>());
5492 std::ostringstream oss; oss << "DataArrayInt::accumulatePerChunck : At rank #" << i << " the input index array points to id " << j << " should be in [0," << nbOfTuples << ") !";
5493 throw INTERP_KERNEL::Exception(oss.str().c_str());
5499 std::ostringstream oss; oss << "DataArrayInt::accumulatePerChunck : At rank #" << i << " the input index array is not in ascendingly sorted.";
5500 throw INTERP_KERNEL::Exception(oss.str().c_str());
5503 ret->copyStringInfoFrom(*this);
5508 * Returns a new DataArrayInt by concatenating two given arrays, so that (1) the number
5509 * of tuples in the result array is <em> a1->getNumberOfTuples() + a2->getNumberOfTuples() -
5510 * offsetA2</em> and (2)
5511 * the number of component in the result array is same as that of each of given arrays.
5512 * First \a offsetA2 tuples of \a a2 are skipped and thus are missing from the result array.
5513 * Info on components is copied from the first of the given arrays. Number of components
5514 * in the given arrays must be the same.
5515 * \param [in] a1 - an array to include in the result array.
5516 * \param [in] a2 - another array to include in the result array.
5517 * \param [in] offsetA2 - number of tuples of \a a2 to skip.
5518 * \return DataArrayInt * - the new instance of DataArrayInt.
5519 * The caller is to delete this result array using decrRef() as it is no more
5521 * \throw If either \a a1 or \a a2 is NULL.
5522 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents().
5524 DataArrayInt *DataArrayInt::Aggregate(const DataArrayInt *a1, const DataArrayInt *a2, int offsetA2)
5527 throw INTERP_KERNEL::Exception("DataArrayInt::Aggregate : input DataArrayInt instance is NULL !");
5528 int nbOfComp=a1->getNumberOfComponents();
5529 if(nbOfComp!=a2->getNumberOfComponents())
5530 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Aggregation !");
5531 int nbOfTuple1=a1->getNumberOfTuples();
5532 int nbOfTuple2=a2->getNumberOfTuples();
5533 DataArrayInt *ret=DataArrayInt::New();
5534 ret->alloc(nbOfTuple1+nbOfTuple2-offsetA2,nbOfComp);
5535 int *pt=std::copy(a1->getConstPointer(),a1->getConstPointer()+nbOfTuple1*nbOfComp,ret->getPointer());
5536 std::copy(a2->getConstPointer()+offsetA2*nbOfComp,a2->getConstPointer()+nbOfTuple2*nbOfComp,pt);
5537 ret->copyStringInfoFrom(*a1);
5542 * Returns a new DataArrayInt by concatenating all given arrays, so that (1) the number
5543 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
5544 * the number of component in the result array is same as that of each of given arrays.
5545 * Info on components is copied from the first of the given arrays. Number of components
5546 * in the given arrays must be the same.
5547 * If the number of non null of elements in \a arr is equal to one the returned object is a copy of it
5548 * not the object itself.
5549 * \param [in] arr - a sequence of arrays to include in the result array.
5550 * \return DataArrayInt * - the new instance of DataArrayInt.
5551 * The caller is to delete this result array using decrRef() as it is no more
5553 * \throw If all arrays within \a arr are NULL.
5554 * \throw If getNumberOfComponents() of arrays within \a arr.
5556 DataArrayInt *DataArrayInt::Aggregate(const std::vector<const DataArrayInt *>& arr)
5558 std::vector<const DataArrayInt *> a;
5559 for(std::vector<const DataArrayInt *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
5563 throw INTERP_KERNEL::Exception("DataArrayInt::Aggregate : input list must be NON EMPTY !");
5564 std::vector<const DataArrayInt *>::const_iterator it=a.begin();
5565 int nbOfComp=(*it)->getNumberOfComponents();
5566 int nbt=(*it++)->getNumberOfTuples();
5567 for(int i=1;it!=a.end();it++,i++)
5569 if((*it)->getNumberOfComponents()!=nbOfComp)
5570 throw INTERP_KERNEL::Exception("DataArrayInt::Aggregate : Nb of components mismatch for array aggregation !");
5571 nbt+=(*it)->getNumberOfTuples();
5573 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5574 ret->alloc(nbt,nbOfComp);
5575 int *pt=ret->getPointer();
5576 for(it=a.begin();it!=a.end();it++)
5577 pt=std::copy((*it)->getConstPointer(),(*it)->getConstPointer()+(*it)->getNbOfElems(),pt);
5578 ret->copyStringInfoFrom(*(a[0]));
5583 * This method takes as input a list of DataArrayInt instances \a arrs that represent each a packed index arrays.
5584 * A packed index array is an allocated array with one component, and at least one tuple. The first element
5585 * of each array in \a arrs must be 0. Each array in \a arrs is expected to be increasingly monotonic.
5586 * This method is useful for users that want to aggregate a pair of DataArrayInt representing an indexed data (typically nodal connectivity index in unstructured meshes.
5588 * \return DataArrayInt * - a new object to be managed by the caller.
5590 DataArrayInt *DataArrayInt::AggregateIndexes(const std::vector<const DataArrayInt *>& arrs)
5593 for(std::vector<const DataArrayInt *>::const_iterator it4=arrs.begin();it4!=arrs.end();it4++)
5597 (*it4)->checkAllocated();
5598 if((*it4)->getNumberOfComponents()!=1)
5600 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a DataArrayInt instance with nb of compo != 1 at pos " << std::distance(arrs.begin(),it4) << " !";
5601 throw INTERP_KERNEL::Exception(oss.str().c_str());
5603 int nbTupl=(*it4)->getNumberOfTuples();
5606 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a DataArrayInt instance with nb of tuples < 1 at pos " << std::distance(arrs.begin(),it4) << " !";
5607 throw INTERP_KERNEL::Exception(oss.str().c_str());
5609 if((*it4)->front()!=0)
5611 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a DataArrayInt instance with front value != 0 at pos " << std::distance(arrs.begin(),it4) << " !";
5612 throw INTERP_KERNEL::Exception(oss.str().c_str());
5618 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a null instance at pos " << std::distance(arrs.begin(),it4) << " !";
5619 throw INTERP_KERNEL::Exception(oss.str().c_str());
5623 throw INTERP_KERNEL::Exception("DataArrayInt::AggregateIndexes : input list must be NON EMPTY !");
5624 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5625 ret->alloc(retSz,1);
5626 int *pt=ret->getPointer(); *pt++=0;
5627 for(std::vector<const DataArrayInt *>::const_iterator it=arrs.begin();it!=arrs.end();it++)
5628 pt=std::transform((*it)->begin()+1,(*it)->end(),pt,std::bind2nd(std::plus<int>(),pt[-1]));
5629 ret->copyStringInfoFrom(*(arrs[0]));
5634 * Returns in a single walk in \a this the min value and the max value in \a this.
5635 * \a this is expected to be single component array.
5637 * \param [out] minValue - the min value in \a this.
5638 * \param [out] maxValue - the max value in \a this.
5640 * \sa getMinValueInArray, getMinValue, getMaxValueInArray, getMaxValue
5642 void DataArrayInt::getMinMaxValues(int& minValue, int& maxValue) const
5645 if(getNumberOfComponents()!=1)
5646 throw INTERP_KERNEL::Exception("DataArrayInt::getMinMaxValues : must be applied on DataArrayInt with only one component !");
5647 int nbTuples(getNumberOfTuples());
5648 const int *pt(begin());
5649 minValue=std::numeric_limits<int>::max(); maxValue=-std::numeric_limits<int>::max();
5650 for(int i=0;i<nbTuples;i++,pt++)
5660 * Converts every value of \a this array to its absolute value.
5661 * \b WARNING this method is non const. If a new DataArrayInt instance should be built containing the result of abs DataArrayInt::computeAbs
5662 * should be called instead.
5664 * \throw If \a this is not allocated.
5665 * \sa DataArrayInt::computeAbs
5667 void DataArrayInt::abs()
5670 int *ptr(getPointer());
5671 std::size_t nbOfElems(getNbOfElems());
5672 std::transform(ptr,ptr+nbOfElems,ptr,std::ptr_fun<int,int>(std::abs));
5677 * This method builds a new instance of \a this object containing the result of std::abs applied of all elements in \a this.
5678 * This method is a const method (that do not change any values in \a this) contrary to DataArrayInt::abs method.
5680 * \return DataArrayInt * - the new instance of DataArrayInt containing the
5681 * same number of tuples and component as \a this array.
5682 * The caller is to delete this result array using decrRef() as it is no more
5684 * \throw If \a this is not allocated.
5685 * \sa DataArrayInt::abs
5687 DataArrayInt *DataArrayInt::computeAbs() const
5690 DataArrayInt *newArr(DataArrayInt::New());
5691 int nbOfTuples(getNumberOfTuples());
5692 int nbOfComp(getNumberOfComponents());
5693 newArr->alloc(nbOfTuples,nbOfComp);
5694 std::transform(begin(),end(),newArr->getPointer(),std::ptr_fun<int,int>(std::abs));
5695 newArr->copyStringInfoFrom(*this);
5700 * Modify all elements of \a this array, so that
5701 * an element _x_ becomes \f$ numerator / x \f$.
5702 * \warning If an exception is thrown because of presence of 0 element in \a this
5703 * array, all elements processed before detection of the zero element remain
5705 * \param [in] numerator - the numerator used to modify array elements.
5706 * \throw If \a this is not allocated.
5707 * \throw If there is an element equal to 0 in \a this array.
5709 void DataArrayInt::applyInv(int numerator)
5712 int *ptr=getPointer();
5713 std::size_t nbOfElems=getNbOfElems();
5714 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
5718 *ptr=numerator/(*ptr);
5722 std::ostringstream oss; oss << "DataArrayInt::applyInv : presence of null value in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
5724 throw INTERP_KERNEL::Exception(oss.str().c_str());
5731 * Modify all elements of \a this array, so that
5732 * an element _x_ becomes \f$ x / val \f$.
5733 * \param [in] val - the denominator used to modify array elements.
5734 * \throw If \a this is not allocated.
5735 * \throw If \a val == 0.
5737 void DataArrayInt::applyDivideBy(int val)
5740 throw INTERP_KERNEL::Exception("DataArrayInt::applyDivideBy : Trying to divide by 0 !");
5742 int *ptr=getPointer();
5743 std::size_t nbOfElems=getNbOfElems();
5744 std::transform(ptr,ptr+nbOfElems,ptr,std::bind2nd(std::divides<int>(),val));
5749 * Modify all elements of \a this array, so that
5750 * an element _x_ becomes <em> x % val </em>.
5751 * \param [in] val - the divisor used to modify array elements.
5752 * \throw If \a this is not allocated.
5753 * \throw If \a val <= 0.
5755 void DataArrayInt::applyModulus(int val)
5758 throw INTERP_KERNEL::Exception("DataArrayInt::applyDivideBy : Trying to operate modulus on value <= 0 !");
5760 int *ptr=getPointer();
5761 std::size_t nbOfElems=getNbOfElems();
5762 std::transform(ptr,ptr+nbOfElems,ptr,std::bind2nd(std::modulus<int>(),val));
5767 * This method works only on data array with one component.
5768 * This method returns a newly allocated array storing stored ascendantly tuple ids in \b this so that
5769 * this[*id] in [\b vmin,\b vmax)
5771 * \param [in] vmin begin of range. This value is included in range (included).
5772 * \param [in] vmax end of range. This value is \b not included in range (excluded).
5773 * \return a newly allocated data array that the caller should deal with.
5775 * \sa DataArrayInt::findIdsNotInRange , DataArrayInt::findIdsStricltyNegative
5777 DataArrayInt *DataArrayInt::findIdsInRange(int vmin, int vmax) const
5779 InRange<int> ir(vmin,vmax);
5780 MCAuto<DataArrayInt> ret(findIdsAdv(ir));
5785 * This method works only on data array with one component.
5786 * This method returns a newly allocated array storing stored ascendantly tuple ids in \b this so that
5787 * this[*id] \b not in [\b vmin,\b vmax)
5789 * \param [in] vmin begin of range. This value is \b not included in range (excluded).
5790 * \param [in] vmax end of range. This value is included in range (included).
5791 * \return a newly allocated data array that the caller should deal with.
5793 * \sa DataArrayInt::findIdsInRange , DataArrayInt::findIdsStricltyNegative
5795 DataArrayInt *DataArrayInt::findIdsNotInRange(int vmin, int vmax) const
5797 NotInRange<int> nir(vmin,vmax);
5798 MCAuto<DataArrayInt> ret(findIdsAdv(nir));
5803 * This method works only on data array with one component.
5804 * This method checks that all ids in \b this are in [ \b vmin, \b vmax ). If there is at least one element in \a this not in [ \b vmin, \b vmax ) an exception will be thrown.
5806 * \param [in] vmin begin of range. This value is included in range (included).
5807 * \param [in] vmax end of range. This value is \b not included in range (excluded).
5808 * \return if all ids in \a this are so that (*this)[i]==i for all i in [ 0, \c this->getNumberOfTuples() ). */
5809 bool DataArrayInt::checkAllIdsInRange(int vmin, int vmax) const
5812 if(getNumberOfComponents()!=1)
5813 throw INTERP_KERNEL::Exception("DataArrayInt::checkAllIdsInRange : this must have exactly one component !");
5814 int nbOfTuples=getNumberOfTuples();
5816 const int *cptr=getConstPointer();
5817 for(int i=0;i<nbOfTuples;i++,cptr++)
5819 if(*cptr>=vmin && *cptr<vmax)
5820 { ret=ret && *cptr==i; }
5823 std::ostringstream oss; oss << "DataArrayInt::checkAllIdsInRange : tuple #" << i << " has value " << *cptr << " should be in [" << vmin << "," << vmax << ") !";
5824 throw INTERP_KERNEL::Exception(oss.str().c_str());
5831 * Modify all elements of \a this array, so that
5832 * an element _x_ becomes <em> val % x </em>.
5833 * \warning If an exception is thrown because of presence of an element <= 0 in \a this
5834 * array, all elements processed before detection of the zero element remain
5836 * \param [in] val - the divident used to modify array elements.
5837 * \throw If \a this is not allocated.
5838 * \throw If there is an element equal to or less than 0 in \a this array.
5840 void DataArrayInt::applyRModulus(int val)
5843 int *ptr=getPointer();
5844 std::size_t nbOfElems=getNbOfElems();
5845 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
5853 std::ostringstream oss; oss << "DataArrayInt::applyRModulus : presence of value <=0 in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
5855 throw INTERP_KERNEL::Exception(oss.str().c_str());
5862 * Modify all elements of \a this array, so that
5863 * an element _x_ becomes <em> val ^ x </em>.
5864 * \param [in] val - the value used to apply pow on all array elements.
5865 * \throw If \a this is not allocated.
5866 * \throw If \a val < 0.
5868 void DataArrayInt::applyPow(int val)
5872 throw INTERP_KERNEL::Exception("DataArrayInt::applyPow : input pow in < 0 !");
5873 int *ptr=getPointer();
5874 std::size_t nbOfElems=getNbOfElems();
5877 std::fill(ptr,ptr+nbOfElems,1);
5880 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
5883 for(int j=0;j<val;j++)
5891 * Modify all elements of \a this array, so that
5892 * an element _x_ becomes \f$ val ^ x \f$.
5893 * \param [in] val - the value used to apply pow on all array elements.
5894 * \throw If \a this is not allocated.
5895 * \throw If there is an element < 0 in \a this array.
5896 * \warning If an exception is thrown because of presence of 0 element in \a this
5897 * array, all elements processed before detection of the zero element remain
5900 void DataArrayInt::applyRPow(int val)
5903 int *ptr=getPointer();
5904 std::size_t nbOfElems=getNbOfElems();
5905 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
5910 for(int j=0;j<*ptr;j++)
5916 std::ostringstream oss; oss << "DataArrayInt::applyRPow : presence of negative value in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
5918 throw INTERP_KERNEL::Exception(oss.str().c_str());
5925 * Returns a new DataArrayInt which is a minimal partition of elements of \a groups.
5926 * The i-th item of the result array is an ID of a set of elements belonging to a
5927 * unique set of groups, which the i-th element is a part of. This set of elements
5928 * belonging to a unique set of groups is called \a family, so the result array contains
5929 * IDs of families each element belongs to.
5931 * \b Example: if we have two groups of elements: \a group1 [0,4] and \a group2 [ 0,1,2 ],
5932 * then there are 3 families:
5933 * - \a family1 (with ID 1) contains element [0] belonging to ( \a group1 + \a group2 ),
5934 * - \a family2 (with ID 2) contains elements [4] belonging to ( \a group1 ),
5935 * - \a family3 (with ID 3) contains element [1,2] belonging to ( \a group2 ), <br>
5936 * and the result array contains IDs of families [ 1,3,3,0,2 ]. <br> Note a family ID 0 which
5937 * stands for the element #3 which is in none of groups.
5939 * \param [in] groups - sequence of groups of element IDs.
5940 * \param [in] newNb - total number of elements; it must be more than max ID of element
5942 * \param [out] fidsOfGroups - IDs of families the elements of each group belong to.
5943 * \return DataArrayInt * - a new instance of DataArrayInt containing IDs of families
5944 * each element with ID from range [0, \a newNb ) belongs to. The caller is to
5945 * delete this array using decrRef() as it is no more needed.
5946 * \throw If any element ID in \a groups violates condition ( 0 <= ID < \a newNb ).
5948 DataArrayInt *DataArrayInt::MakePartition(const std::vector<const DataArrayInt *>& groups, int newNb, std::vector< std::vector<int> >& fidsOfGroups)
5950 std::vector<const DataArrayInt *> groups2;
5951 for(std::vector<const DataArrayInt *>::const_iterator it4=groups.begin();it4!=groups.end();it4++)
5953 groups2.push_back(*it4);
5954 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5955 ret->alloc(newNb,1);
5956 int *retPtr=ret->getPointer();
5957 std::fill(retPtr,retPtr+newNb,0);
5959 for(std::vector<const DataArrayInt *>::const_iterator iter=groups2.begin();iter!=groups2.end();iter++)
5961 const int *ptr=(*iter)->getConstPointer();
5962 std::size_t nbOfElem=(*iter)->getNbOfElems();
5964 for(int j=0;j<sfid;j++)
5967 for(std::size_t i=0;i<nbOfElem;i++)
5969 if(ptr[i]>=0 && ptr[i]<newNb)
5971 if(retPtr[ptr[i]]==j)
5979 std::ostringstream oss; oss << "DataArrayInt::MakePartition : In group \"" << (*iter)->getName() << "\" in tuple #" << i << " value = " << ptr[i] << " ! Should be in [0," << newNb;
5981 throw INTERP_KERNEL::Exception(oss.str().c_str());
5988 fidsOfGroups.clear();
5989 fidsOfGroups.resize(groups2.size());
5991 for(std::vector<const DataArrayInt *>::const_iterator iter=groups2.begin();iter!=groups2.end();iter++,grId++)
5994 const int *ptr=(*iter)->getConstPointer();
5995 std::size_t nbOfElem=(*iter)->getNbOfElems();
5996 for(const int *p=ptr;p!=ptr+nbOfElem;p++)
5997 tmp.insert(retPtr[*p]);
5998 fidsOfGroups[grId].insert(fidsOfGroups[grId].end(),tmp.begin(),tmp.end());
6004 * Returns a new DataArrayInt which contains all elements of given one-dimensional
6005 * arrays. The result array does not contain any duplicates and its values
6006 * are sorted in ascending order.
6007 * \param [in] arr - sequence of DataArrayInt's to unite.
6008 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6009 * array using decrRef() as it is no more needed.
6010 * \throw If any \a arr[i] is not allocated.
6011 * \throw If \a arr[i]->getNumberOfComponents() != 1.
6013 DataArrayInt *DataArrayInt::BuildUnion(const std::vector<const DataArrayInt *>& arr)
6015 std::vector<const DataArrayInt *> a;
6016 for(std::vector<const DataArrayInt *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
6019 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
6021 (*it)->checkAllocated();
6022 if((*it)->getNumberOfComponents()!=1)
6023 throw INTERP_KERNEL::Exception("DataArrayInt::BuildUnion : only single component allowed !");
6027 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
6029 const int *pt=(*it)->getConstPointer();
6030 int nbOfTuples=(*it)->getNumberOfTuples();
6031 r.insert(pt,pt+nbOfTuples);
6033 DataArrayInt *ret=DataArrayInt::New();
6034 ret->alloc((int)r.size(),1);
6035 std::copy(r.begin(),r.end(),ret->getPointer());
6040 * Returns a new DataArrayInt which contains elements present in each of given one-dimensional
6041 * arrays. The result array does not contain any duplicates and its values
6042 * are sorted in ascending order.
6043 * \param [in] arr - sequence of DataArrayInt's to intersect.
6044 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6045 * array using decrRef() as it is no more needed.
6046 * \throw If any \a arr[i] is not allocated.
6047 * \throw If \a arr[i]->getNumberOfComponents() != 1.
6049 DataArrayInt *DataArrayInt::BuildIntersection(const std::vector<const DataArrayInt *>& arr)
6051 std::vector<const DataArrayInt *> a;
6052 for(std::vector<const DataArrayInt *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
6055 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
6057 (*it)->checkAllocated();
6058 if((*it)->getNumberOfComponents()!=1)
6059 throw INTERP_KERNEL::Exception("DataArrayInt::BuildIntersection : only single component allowed !");
6063 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
6065 const int *pt=(*it)->getConstPointer();
6066 int nbOfTuples=(*it)->getNumberOfTuples();
6067 std::set<int> s1(pt,pt+nbOfTuples);
6071 std::set_intersection(r.begin(),r.end(),s1.begin(),s1.end(),inserter(r2,r2.end()));
6077 DataArrayInt *ret(DataArrayInt::New());
6078 ret->alloc((int)r.size(),1);
6079 std::copy(r.begin(),r.end(),ret->getPointer());
6084 namespace MEDCouplingImpl
6089 OpSwitchedOn(int *pt):_pt(pt),_cnt(0) { }
6090 void operator()(const bool& b) { if(b) *_pt++=_cnt; _cnt++; }
6099 OpSwitchedOff(int *pt):_pt(pt),_cnt(0) { }
6100 void operator()(const bool& b) { if(!b) *_pt++=_cnt; _cnt++; }
6109 * This method returns the list of ids in ascending mode so that v[id]==true.
6111 DataArrayInt *DataArrayInt::BuildListOfSwitchedOn(const std::vector<bool>& v)
6113 int sz((int)std::count(v.begin(),v.end(),true));
6114 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(sz,1);
6115 std::for_each(v.begin(),v.end(),MEDCouplingImpl::OpSwitchedOn(ret->getPointer()));
6120 * This method returns the list of ids in ascending mode so that v[id]==false.
6122 DataArrayInt *DataArrayInt::BuildListOfSwitchedOff(const std::vector<bool>& v)
6124 int sz((int)std::count(v.begin(),v.end(),false));
6125 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(sz,1);
6126 std::for_each(v.begin(),v.end(),MEDCouplingImpl::OpSwitchedOff(ret->getPointer()));
6131 * This method allows to put a vector of vector of integer into a more compact data stucture (skyline).
6132 * This method is not available into python because no available optimized data structure available to map std::vector< std::vector<int> >.
6134 * \param [in] v the input data structure to be translate into skyline format.
6135 * \param [out] data the first element of the skyline format. The user is expected to deal with newly allocated array.
6136 * \param [out] dataIndex the second element of the skyline format.
6138 void DataArrayInt::PutIntoToSkylineFrmt(const std::vector< std::vector<int> >& v, DataArrayInt *& data, DataArrayInt *& dataIndex)
6140 int sz((int)v.size());
6141 MCAuto<DataArrayInt> ret0(DataArrayInt::New()),ret1(DataArrayInt::New());
6142 ret1->alloc(sz+1,1);
6143 int *pt(ret1->getPointer()); *pt=0;
6144 for(int i=0;i<sz;i++,pt++)
6145 pt[1]=pt[0]+(int)v[i].size();
6146 ret0->alloc(ret1->back(),1);
6147 pt=ret0->getPointer();
6148 for(int i=0;i<sz;i++)
6149 pt=std::copy(v[i].begin(),v[i].end(),pt);
6150 data=ret0.retn(); dataIndex=ret1.retn();
6154 * Returns a new DataArrayInt which contains a complement of elements of \a this
6155 * one-dimensional array. I.e. the result array contains all elements from the range [0,
6156 * \a nbOfElement) not present in \a this array.
6157 * \param [in] nbOfElement - maximal size of the result array.
6158 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6159 * array using decrRef() as it is no more needed.
6160 * \throw If \a this is not allocated.
6161 * \throw If \a this->getNumberOfComponents() != 1.
6162 * \throw If any element \a x of \a this array violates condition ( 0 <= \a x < \a
6165 DataArrayInt *DataArrayInt::buildComplement(int nbOfElement) const
6168 if(getNumberOfComponents()!=1)
6169 throw INTERP_KERNEL::Exception("DataArrayInt::buildComplement : only single component allowed !");
6170 std::vector<bool> tmp(nbOfElement);
6171 const int *pt=getConstPointer();
6172 int nbOfTuples=getNumberOfTuples();
6173 for(const int *w=pt;w!=pt+nbOfTuples;w++)
6174 if(*w>=0 && *w<nbOfElement)
6177 throw INTERP_KERNEL::Exception("DataArrayInt::buildComplement : an element is not in valid range : [0,nbOfElement) !");
6178 int nbOfRetVal=(int)std::count(tmp.begin(),tmp.end(),false);
6179 DataArrayInt *ret=DataArrayInt::New();
6180 ret->alloc(nbOfRetVal,1);
6182 int *retPtr=ret->getPointer();
6183 for(int i=0;i<nbOfElement;i++)
6190 * Returns a new DataArrayInt containing elements of \a this one-dimensional missing
6191 * from an \a other one-dimensional array.
6192 * \param [in] other - a DataArrayInt containing elements not to include in the result array.
6193 * \return DataArrayInt * - a new instance of DataArrayInt with one component. The
6194 * caller is to delete this array using decrRef() as it is no more needed.
6195 * \throw If \a other is NULL.
6196 * \throw If \a other is not allocated.
6197 * \throw If \a other->getNumberOfComponents() != 1.
6198 * \throw If \a this is not allocated.
6199 * \throw If \a this->getNumberOfComponents() != 1.
6200 * \sa DataArrayInt::buildSubstractionOptimized()
6202 DataArrayInt *DataArrayInt::buildSubstraction(const DataArrayInt *other) const
6205 throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstraction : DataArrayInt pointer in input is NULL !");
6207 other->checkAllocated();
6208 if(getNumberOfComponents()!=1)
6209 throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstraction : only single component allowed !");
6210 if(other->getNumberOfComponents()!=1)
6211 throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstraction : only single component allowed for other type !");
6212 const int *pt=getConstPointer();
6213 int nbOfTuples=getNumberOfTuples();
6214 std::set<int> s1(pt,pt+nbOfTuples);
6215 pt=other->getConstPointer();
6216 nbOfTuples=other->getNumberOfTuples();
6217 std::set<int> s2(pt,pt+nbOfTuples);
6219 std::set_difference(s1.begin(),s1.end(),s2.begin(),s2.end(),std::back_insert_iterator< std::vector<int> >(r));
6220 DataArrayInt *ret=DataArrayInt::New();
6221 ret->alloc((int)r.size(),1);
6222 std::copy(r.begin(),r.end(),ret->getPointer());
6227 * \a this is expected to have one component and to be sorted ascendingly (as for \a other).
6228 * \a other is expected to be a part of \a this. If not DataArrayInt::buildSubstraction should be called instead.
6230 * \param [in] other an array with one component and expected to be sorted ascendingly.
6231 * \ret list of ids in \a this but not in \a other.
6232 * \sa DataArrayInt::buildSubstraction
6234 DataArrayInt *DataArrayInt::buildSubstractionOptimized(const DataArrayInt *other) const
6236 static const char *MSG="DataArrayInt::buildSubstractionOptimized : only single component allowed !";
6237 if(!other) throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstractionOptimized : NULL input array !");
6238 checkAllocated(); other->checkAllocated();
6239 if(getNumberOfComponents()!=1) throw INTERP_KERNEL::Exception(MSG);
6240 if(other->getNumberOfComponents()!=1) throw INTERP_KERNEL::Exception(MSG);
6241 const int *pt1Bg(begin()),*pt1End(end()),*pt2Bg(other->begin()),*pt2End(other->end());
6242 const int *work1(pt1Bg),*work2(pt2Bg);
6243 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
6244 for(;work1!=pt1End;work1++)
6246 if(work2!=pt2End && *work1==*work2)
6249 ret->pushBackSilent(*work1);
6256 * Returns a new DataArrayInt which contains all elements of \a this and a given
6257 * one-dimensional arrays. The result array does not contain any duplicates
6258 * and its values are sorted in ascending order.
6259 * \param [in] other - an array to unite with \a this one.
6260 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6261 * array using decrRef() as it is no more needed.
6262 * \throw If \a this or \a other is not allocated.
6263 * \throw If \a this->getNumberOfComponents() != 1.
6264 * \throw If \a other->getNumberOfComponents() != 1.
6266 DataArrayInt *DataArrayInt::buildUnion(const DataArrayInt *other) const
6268 std::vector<const DataArrayInt *>arrs(2);
6269 arrs[0]=this; arrs[1]=other;
6270 return BuildUnion(arrs);
6275 * Returns a new DataArrayInt which contains elements present in both \a this and a given
6276 * one-dimensional arrays. The result array does not contain any duplicates
6277 * and its values are sorted in ascending order.
6278 * \param [in] other - an array to intersect with \a this one.
6279 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6280 * array using decrRef() as it is no more needed.
6281 * \throw If \a this or \a other is not allocated.
6282 * \throw If \a this->getNumberOfComponents() != 1.
6283 * \throw If \a other->getNumberOfComponents() != 1.
6285 DataArrayInt *DataArrayInt::buildIntersection(const DataArrayInt *other) const
6287 std::vector<const DataArrayInt *>arrs(2);
6288 arrs[0]=this; arrs[1]=other;
6289 return BuildIntersection(arrs);
6293 * This method can be applied on allocated with one component DataArrayInt instance.
6294 * This method is typically relevant for sorted arrays. All consecutive duplicated items in \a this will appear only once in returned DataArrayInt instance.
6295 * Example : if \a this contains [1,2,2,3,3,3,3,4,5,5,7,7,7,19] the returned array will contain [1,2,3,4,5,7,19]
6297 * \return a newly allocated array that contain the result of the unique operation applied on \a this.
6298 * \throw if \a this is not allocated or if \a this has not exactly one component.
6299 * \sa DataArrayInt::buildUniqueNotSorted
6301 DataArrayInt *DataArrayInt::buildUnique() const
6304 if(getNumberOfComponents()!=1)
6305 throw INTERP_KERNEL::Exception("DataArrayInt::buildUnique : only single component allowed !");
6306 int nbOfTuples=getNumberOfTuples();
6307 MCAuto<DataArrayInt> tmp=deepCopy();
6308 int *data=tmp->getPointer();
6309 int *last=std::unique(data,data+nbOfTuples);
6310 MCAuto<DataArrayInt> ret=DataArrayInt::New();
6311 ret->alloc(std::distance(data,last),1);
6312 std::copy(data,last,ret->getPointer());
6317 * This method can be applied on allocated with one component DataArrayInt instance.
6318 * This method keep elements only once by keeping the same order in \a this that is not expected to be sorted.
6320 * \return a newly allocated array that contain the result of the unique operation applied on \a this.
6322 * \throw if \a this is not allocated or if \a this has not exactly one component.
6324 * \sa DataArrayInt::buildUnique
6326 DataArrayInt *DataArrayInt::buildUniqueNotSorted() const
6329 if(getNumberOfComponents()!=1)
6330 throw INTERP_KERNEL::Exception("DataArrayInt::buildUniqueNotSorted : only single component allowed !");
6332 getMinMaxValues(minVal,maxVal);
6333 std::vector<bool> b(maxVal-minVal+1,false);
6334 const int *ptBg(begin()),*endBg(end());
6335 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
6336 for(const int *pt=ptBg;pt!=endBg;pt++)
6340 ret->pushBackSilent(*pt);
6344 ret->copyStringInfoFrom(*this);
6349 * Returns a new DataArrayInt which contains size of every of groups described by \a this
6350 * "index" array. Such "index" array is returned for example by
6351 * \ref MEDCoupling::MEDCouplingUMesh::buildDescendingConnectivity
6352 * "MEDCouplingUMesh::buildDescendingConnectivity" and
6353 * \ref MEDCoupling::MEDCouplingUMesh::getNodalConnectivityIndex
6354 * "MEDCouplingUMesh::getNodalConnectivityIndex" etc.
6355 * This method preforms the reverse operation of DataArrayInt::computeOffsetsFull.
6356 * \return DataArrayInt * - a new instance of DataArrayInt, whose number of tuples
6357 * equals to \a this->getNumberOfComponents() - 1, and number of components is 1.
6358 * The caller is to delete this array using decrRef() as it is no more needed.
6359 * \throw If \a this is not allocated.
6360 * \throw If \a this->getNumberOfComponents() != 1.
6361 * \throw If \a this->getNumberOfTuples() < 2.
6364 * - this contains [1,3,6,7,7,9,15]
6365 * - result array contains [2,3,1,0,2,6],
6366 * where 2 = 3 - 1, 3 = 6 - 3, 1 = 7 - 6 etc.
6368 * \sa DataArrayInt::computeOffsetsFull
6370 DataArrayInt *DataArrayInt::deltaShiftIndex() const
6373 if(getNumberOfComponents()!=1)
6374 throw INTERP_KERNEL::Exception("DataArrayInt::deltaShiftIndex : only single component allowed !");
6375 int nbOfTuples=getNumberOfTuples();
6377 throw INTERP_KERNEL::Exception("DataArrayInt::deltaShiftIndex : 1 tuple at least must be present in 'this' !");
6378 const int *ptr=getConstPointer();
6379 DataArrayInt *ret=DataArrayInt::New();
6380 ret->alloc(nbOfTuples-1,1);
6381 int *out=ret->getPointer();
6382 std::transform(ptr+1,ptr+nbOfTuples,ptr,out,std::minus<int>());
6387 * Modifies \a this one-dimensional array so that value of each element \a x
6388 * of \a this array (\a a) is computed as \f$ x_i = \sum_{j=0}^{i-1} a[ j ] \f$.
6389 * Or: for each i>0 new[i]=new[i-1]+old[i-1] for i==0 new[i]=0. Number of tuples
6390 * and components remains the same.<br>
6391 * This method is useful for allToAllV in MPI with contiguous policy. This method
6392 * differs from computeOffsetsFull() in that the number of tuples is \b not changed by
6394 * \throw If \a this is not allocated.
6395 * \throw If \a this->getNumberOfComponents() != 1.
6398 * - Before \a this contains [3,5,1,2,0,8]
6399 * - After \a this contains [0,3,8,9,11,11]<br>
6400 * Note that the last element 19 = 11 + 8 is missing because size of \a this
6401 * array is retained and thus there is no space to store the last element.
6403 void DataArrayInt::computeOffsets()
6406 if(getNumberOfComponents()!=1)
6407 throw INTERP_KERNEL::Exception("DataArrayInt::computeOffsets : only single component allowed !");
6408 int nbOfTuples=getNumberOfTuples();
6411 int *work=getPointer();
6414 for(int i=1;i<nbOfTuples;i++)
6417 work[i]=work[i-1]+tmp;
6425 * Modifies \a this one-dimensional array so that value of each element \a x
6426 * of \a this array (\a a) is computed as \f$ x_i = \sum_{j=0}^{i-1} a[ j ] \f$.
6427 * Or: for each i>0 new[i]=new[i-1]+old[i-1] for i==0 new[i]=0. Number
6428 * components remains the same and number of tuples is inceamented by one.<br>
6429 * This method is useful for allToAllV in MPI with contiguous policy. This method
6430 * differs from computeOffsets() in that the number of tuples is changed by this one.
6431 * This method preforms the reverse operation of DataArrayInt::deltaShiftIndex.
6432 * \throw If \a this is not allocated.
6433 * \throw If \a this->getNumberOfComponents() != 1.
6436 * - Before \a this contains [3,5,1,2,0,8]
6437 * - After \a this contains [0,3,8,9,11,11,19]<br>
6438 * \sa DataArrayInt::deltaShiftIndex
6440 void DataArrayInt::computeOffsetsFull()
6443 if(getNumberOfComponents()!=1)
6444 throw INTERP_KERNEL::Exception("DataArrayInt::computeOffsetsFull : only single component allowed !");
6445 int nbOfTuples=getNumberOfTuples();
6446 int *ret=(int *)malloc((nbOfTuples+1)*sizeof(int));
6447 const int *work=getConstPointer();
6449 for(int i=0;i<nbOfTuples;i++)
6450 ret[i+1]=work[i]+ret[i];
6451 useArray(ret,true,C_DEALLOC,nbOfTuples+1,1);
6456 * Returns two new DataArrayInt instances whose contents is computed from that of \a this and \a listOfIds arrays as follows.
6457 * \a this is expected to be an offset format ( as returned by DataArrayInt::computeOffsetsFull ) that is to say with one component
6458 * and ** sorted strictly increasingly **. \a listOfIds is expected to be sorted ascendingly (not strictly needed for \a listOfIds).
6459 * This methods searches in \a this, considered as a set of contiguous \c this->getNumberOfComponents() ranges, all ids in \a listOfIds
6460 * filling completely one of the ranges in \a this.
6462 * \param [in] listOfIds a list of ids that has to be sorted ascendingly.
6463 * \param [out] rangeIdsFetched the range ids fetched
6464 * \param [out] idsInInputListThatFetch contains the list of ids in \a listOfIds that are \b fully included in a range in \a this. So
6465 * \a idsInInputListThatFetch is a part of input \a listOfIds.
6467 * \sa DataArrayInt::computeOffsetsFull
6470 * - \a this : [0,3,7,9,15,18]
6471 * - \a listOfIds contains [0,1,2,3,7,8,15,16,17]
6472 * - \a rangeIdsFetched result array: [0,2,4]
6473 * - \a idsInInputListThatFetch result array: [0,1,2,7,8,15,16,17]
6474 * In this example id 3 in input \a listOfIds is alone so it do not appear in output \a idsInInputListThatFetch.
6477 void DataArrayInt::findIdsRangesInListOfIds(const DataArrayInt *listOfIds, DataArrayInt *& rangeIdsFetched, DataArrayInt *& idsInInputListThatFetch) const
6480 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsRangesInListOfIds : input list of ids is null !");
6481 listOfIds->checkAllocated(); checkAllocated();
6482 if(listOfIds->getNumberOfComponents()!=1)
6483 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsRangesInListOfIds : input list of ids must have exactly one component !");
6484 if(getNumberOfComponents()!=1)
6485 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsRangesInListOfIds : this must have exactly one component !");
6486 MCAuto<DataArrayInt> ret0=DataArrayInt::New(); ret0->alloc(0,1);
6487 MCAuto<DataArrayInt> ret1=DataArrayInt::New(); ret1->alloc(0,1);
6488 const int *tupEnd(listOfIds->end()),*offBg(begin()),*offEnd(end()-1);
6489 const int *tupPtr(listOfIds->begin()),*offPtr(offBg);
6490 while(tupPtr!=tupEnd && offPtr!=offEnd)
6492 if(*tupPtr==*offPtr)
6495 while(i<offPtr[1] && *tupPtr==i && tupPtr!=tupEnd) { i++; tupPtr++; }
6498 ret0->pushBackSilent((int)std::distance(offBg,offPtr));
6499 ret1->pushBackValsSilent(tupPtr-(offPtr[1]-offPtr[0]),tupPtr);
6504 { if(*tupPtr<*offPtr) tupPtr++; else offPtr++; }
6506 rangeIdsFetched=ret0.retn();
6507 idsInInputListThatFetch=ret1.retn();
6511 * Returns a new DataArrayInt whose contents is computed from that of \a this and \a
6512 * offsets arrays as follows. \a offsets is a one-dimensional array considered as an
6513 * "index" array of a "iota" array, thus, whose each element gives an index of a group
6514 * beginning within the "iota" array. And \a this is a one-dimensional array
6515 * considered as a selector of groups described by \a offsets to include into the result array.
6516 * \throw If \a offsets is NULL.
6517 * \throw If \a offsets is not allocated.
6518 * \throw If \a offsets->getNumberOfComponents() != 1.
6519 * \throw If \a offsets is not monotonically increasing.
6520 * \throw If \a this is not allocated.
6521 * \throw If \a this->getNumberOfComponents() != 1.
6522 * \throw If any element of \a this is not a valid index for \a offsets array.
6525 * - \a this: [0,2,3]
6526 * - \a offsets: [0,3,6,10,14,20]
6527 * - result array: [0,1,2,6,7,8,9,10,11,12,13] == <br>
6528 * \c range(0,3) + \c range(6,10) + \c range(10,14) ==<br>
6529 * \c range( \a offsets[ \a this[0] ], offsets[ \a this[0]+1 ]) +
6530 * \c range( \a offsets[ \a this[1] ], offsets[ \a this[1]+1 ]) +
6531 * \c range( \a offsets[ \a this[2] ], offsets[ \a this[2]+1 ])
6533 DataArrayInt *DataArrayInt::buildExplicitArrByRanges(const DataArrayInt *offsets) const
6536 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrByRanges : DataArrayInt pointer in input is NULL !");
6538 if(getNumberOfComponents()!=1)
6539 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrByRanges : only single component allowed !");
6540 offsets->checkAllocated();
6541 if(offsets->getNumberOfComponents()!=1)
6542 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrByRanges : input array should have only single component !");
6543 int othNbTuples=offsets->getNumberOfTuples()-1;
6544 int nbOfTuples=getNumberOfTuples();
6545 int retNbOftuples=0;
6546 const int *work=getConstPointer();
6547 const int *offPtr=offsets->getConstPointer();
6548 for(int i=0;i<nbOfTuples;i++)
6551 if(val>=0 && val<othNbTuples)
6553 int delta=offPtr[val+1]-offPtr[val];
6555 retNbOftuples+=delta;
6558 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrByRanges : Tuple #" << val << " of offset array has a delta < 0 !";
6559 throw INTERP_KERNEL::Exception(oss.str().c_str());
6564 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrByRanges : Tuple #" << i << " in this contains " << val;
6565 oss << " whereas offsets array is of size " << othNbTuples+1 << " !";
6566 throw INTERP_KERNEL::Exception(oss.str().c_str());
6569 MCAuto<DataArrayInt> ret=DataArrayInt::New();
6570 ret->alloc(retNbOftuples,1);
6571 int *retPtr=ret->getPointer();
6572 for(int i=0;i<nbOfTuples;i++)
6575 int start=offPtr[val];
6576 int off=offPtr[val+1]-start;
6577 for(int j=0;j<off;j++,retPtr++)
6584 * Returns a new DataArrayInt whose contents is computed using \a this that must be a
6585 * scaled array (monotonically increasing).
6586 from that of \a this and \a
6587 * offsets arrays as follows. \a offsets is a one-dimensional array considered as an
6588 * "index" array of a "iota" array, thus, whose each element gives an index of a group
6589 * beginning within the "iota" array. And \a this is a one-dimensional array
6590 * considered as a selector of groups described by \a offsets to include into the result array.
6591 * \throw If \a is NULL.
6592 * \throw If \a this is not allocated.
6593 * \throw If \a this->getNumberOfComponents() != 1.
6594 * \throw If \a this->getNumberOfTuples() == 0.
6595 * \throw If \a this is not monotonically increasing.
6596 * \throw If any element of ids in ( \a bg \a stop \a step ) points outside the scale in \a this.
6599 * - \a bg , \a stop and \a step : (0,5,2)
6600 * - \a this: [0,3,6,10,14,20]
6601 * - result array: [0,0,0, 2,2,2,2, 4,4,4,4,4,4] == <br>
6603 DataArrayInt *DataArrayInt::buildExplicitArrOfSliceOnScaledArr(int bg, int stop, int step) const
6606 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrOfSliceOnScaledArr : not allocated array !");
6607 if(getNumberOfComponents()!=1)
6608 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrOfSliceOnScaledArr : number of components is expected to be equal to one !");
6609 int nbOfTuples(getNumberOfTuples());
6611 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrOfSliceOnScaledArr : number of tuples must be != 0 !");
6612 const int *ids(begin());
6613 int nbOfEltsInSlc(GetNumberOfItemGivenBESRelative(bg,stop,step,"DataArrayInt::buildExplicitArrOfSliceOnScaledArr")),sz(0),pos(bg);
6614 for(int i=0;i<nbOfEltsInSlc;i++,pos+=step)
6616 if(pos>=0 && pos<nbOfTuples-1)
6618 int delta(ids[pos+1]-ids[pos]);
6622 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrOfSliceOnScaledArr : At pos #" << i << " of input slice, value is " << pos << " and at this pos this is not monotonically increasing !";
6623 throw INTERP_KERNEL::Exception(oss.str().c_str());
6628 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrOfSliceOnScaledArr : At pos #" << i << " of input slice, value is " << pos << " should be in [0," << nbOfTuples-1 << ") !";
6629 throw INTERP_KERNEL::Exception(oss.str().c_str());
6632 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(sz,1);
6633 int *retPtr(ret->getPointer());
6635 for(int i=0;i<nbOfEltsInSlc;i++,pos+=step)
6637 int delta(ids[pos+1]-ids[pos]);
6638 for(int j=0;j<delta;j++,retPtr++)
6645 * Given in input ranges \a ranges, it returns a newly allocated DataArrayInt instance having one component and the same number of tuples than \a this.
6646 * For each tuple at place **i** in \a this it tells which is the first range in \a ranges that contains value \c this->getIJ(i,0) and put the result
6647 * in tuple **i** of returned DataArrayInt.
6648 * If ranges overlapped (in theory it should not) this method do not detect it and always returns the first range.
6650 * For example if \a this contains : [1,24,7,8,10,17] and \a ranges contains [(0,3),(3,8),(8,15),(15,22),(22,30)]
6651 * The return DataArrayInt will contain : **[0,4,1,2,2,3]**
6653 * \param [in] ranges typically come from output of MEDCouplingUMesh::ComputeRangesFromTypeDistribution. Each range is specified like this : 1st component is
6654 * for lower value included and 2nd component is the upper value of corresponding range **excluded**.
6655 * \throw If offsets is a null pointer or does not have 2 components or if \a this is not allocated or \a this do not have exactly one component. To finish an exception
6656 * is thrown if no ranges in \a ranges contains value in \a this.
6658 * \sa DataArrayInt::findIdInRangeForEachTuple
6660 DataArrayInt *DataArrayInt::findRangeIdForEachTuple(const DataArrayInt *ranges) const
6663 throw INTERP_KERNEL::Exception("DataArrayInt::findRangeIdForEachTuple : null input pointer !");
6664 if(ranges->getNumberOfComponents()!=2)
6665 throw INTERP_KERNEL::Exception("DataArrayInt::findRangeIdForEachTuple : input DataArrayInt instance should have 2 components !");
6667 if(getNumberOfComponents()!=1)
6668 throw INTERP_KERNEL::Exception("DataArrayInt::findRangeIdForEachTuple : this should have only one component !");
6669 int nbTuples=getNumberOfTuples();
6670 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbTuples,1);
6671 int nbOfRanges=ranges->getNumberOfTuples();
6672 const int *rangesPtr=ranges->getConstPointer();
6673 int *retPtr=ret->getPointer();
6674 const int *inPtr=getConstPointer();
6675 for(int i=0;i<nbTuples;i++,retPtr++)
6679 for(int j=0;j<nbOfRanges && !found;j++)
6680 if(val>=rangesPtr[2*j] && val<rangesPtr[2*j+1])
6681 { *retPtr=j; found=true; }
6686 std::ostringstream oss; oss << "DataArrayInt::findRangeIdForEachTuple : tuple #" << i << " not found by any ranges !";
6687 throw INTERP_KERNEL::Exception(oss.str().c_str());
6694 * Given in input ranges \a ranges, it returns a newly allocated DataArrayInt instance having one component and the same number of tuples than \a this.
6695 * For each tuple at place **i** in \a this it tells which is the sub position of the first range in \a ranges that contains value \c this->getIJ(i,0) and put the result
6696 * in tuple **i** of returned DataArrayInt.
6697 * If ranges overlapped (in theory it should not) this method do not detect it and always returns the sub position of the first range.
6699 * For example if \a this contains : [1,24,7,8,10,17] and \a ranges contains [(0,3),(3,8),(8,15),(15,22),(22,30)]
6700 * The return DataArrayInt will contain : **[1,2,4,0,2,2]**
6701 * This method is often called in pair with DataArrayInt::findRangeIdForEachTuple method.
6703 * \param [in] ranges typically come from output of MEDCouplingUMesh::ComputeRangesFromTypeDistribution. Each range is specified like this : 1st component is
6704 * for lower value included and 2nd component is the upper value of corresponding range **excluded**.
6705 * \throw If offsets is a null pointer or does not have 2 components or if \a this is not allocated or \a this do not have exactly one component. To finish an exception
6706 * is thrown if no ranges in \a ranges contains value in \a this.
6707 * \sa DataArrayInt::findRangeIdForEachTuple
6709 DataArrayInt *DataArrayInt::findIdInRangeForEachTuple(const DataArrayInt *ranges) const
6712 throw INTERP_KERNEL::Exception("DataArrayInt::findIdInRangeForEachTuple : null input pointer !");
6713 if(ranges->getNumberOfComponents()!=2)
6714 throw INTERP_KERNEL::Exception("DataArrayInt::findIdInRangeForEachTuple : input DataArrayInt instance should have 2 components !");
6716 if(getNumberOfComponents()!=1)
6717 throw INTERP_KERNEL::Exception("DataArrayInt::findIdInRangeForEachTuple : this should have only one component !");
6718 int nbTuples=getNumberOfTuples();
6719 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbTuples,1);
6720 int nbOfRanges=ranges->getNumberOfTuples();
6721 const int *rangesPtr=ranges->getConstPointer();
6722 int *retPtr=ret->getPointer();
6723 const int *inPtr=getConstPointer();
6724 for(int i=0;i<nbTuples;i++,retPtr++)
6728 for(int j=0;j<nbOfRanges && !found;j++)
6729 if(val>=rangesPtr[2*j] && val<rangesPtr[2*j+1])
6730 { *retPtr=val-rangesPtr[2*j]; found=true; }
6735 std::ostringstream oss; oss << "DataArrayInt::findIdInRangeForEachTuple : tuple #" << i << " not found by any ranges !";
6736 throw INTERP_KERNEL::Exception(oss.str().c_str());
6743 * \b WARNING this method is a \b non \a const \b method. This method works tuple by tuple. Each tuple is expected to be pairs (number of components must be equal to 2).
6744 * This method rearrange each pair in \a this so that, tuple with id \b tid will be after the call \c this->getIJ(tid,0)==this->getIJ(tid-1,1) and \c this->getIJ(tid,1)==this->getIJ(tid+1,0).
6745 * If it is impossible to reach such condition an exception will be thrown ! \b WARNING In case of throw \a this can be partially modified !
6746 * If this method has correctly worked, \a this will be able to be considered as a linked list.
6747 * This method does nothing if number of tuples is lower of equal to 1.
6749 * This method is useful for users having an unstructured mesh having only SEG2 to rearrange internaly the connectibity without any coordinates consideration.
6751 * \sa MEDCouplingUMesh::orderConsecutiveCells1D, DataArrayInt::fromLinkedListOfPairToList
6753 void DataArrayInt::sortEachPairToMakeALinkedList()
6756 if(getNumberOfComponents()!=2)
6757 throw INTERP_KERNEL::Exception("DataArrayInt::sortEachPairToMakeALinkedList : Only works on DataArrayInt instance with nb of components equal to 2 !");
6758 int nbOfTuples(getNumberOfTuples());
6761 int *conn(getPointer());
6762 for(int i=1;i<nbOfTuples;i++,conn+=2)
6766 if(conn[2]==conn[3])
6768 std::ostringstream oss; oss << "DataArrayInt::sortEachPairToMakeALinkedList : In the tuple #" << i << " presence of a pair filled with same ids !";
6769 throw INTERP_KERNEL::Exception(oss.str().c_str());
6771 if(conn[2]!=conn[1] && conn[3]==conn[1] && conn[2]!=conn[0])
6772 std::swap(conn[2],conn[3]);
6773 //not(conn[2]==conn[1] && conn[3]!=conn[1] && conn[3]!=conn[0])
6774 if(conn[2]!=conn[1] || conn[3]==conn[1] || conn[3]==conn[0])
6776 std::ostringstream oss; oss << "DataArrayInt::sortEachPairToMakeALinkedList : In the tuple #" << i << " something is invalid !";
6777 throw INTERP_KERNEL::Exception(oss.str().c_str());
6782 if(conn[0]==conn[1] || conn[2]==conn[3])
6783 throw INTERP_KERNEL::Exception("DataArrayInt::sortEachPairToMakeALinkedList : In the 2 first tuples presence of a pair filled with same ids !");
6786 s.insert(conn,conn+4);
6788 throw INTERP_KERNEL::Exception("DataArrayInt::sortEachPairToMakeALinkedList : This can't be considered as a linked list regarding 2 first tuples !");
6789 if(std::count(conn,conn+4,conn[0])==2)
6794 if(conn[2]==conn[0])
6798 std::copy(tmp,tmp+4,conn);
6801 {//here we are sure to have (std::count(conn,conn+4,conn[1])==2)
6802 if(conn[1]==conn[3])
6803 std::swap(conn[2],conn[3]);
6810 * \a this is expected to be a correctly linked list of pairs.
6812 * \sa DataArrayInt::sortEachPairToMakeALinkedList
6814 MCAuto<DataArrayInt> DataArrayInt::fromLinkedListOfPairToList() const
6817 checkNbOfComps(2,"DataArrayInt::fromLinkedListOfPairToList : this is expected to have 2 components");
6818 int nbTuples(getNumberOfTuples());
6820 throw INTERP_KERNEL::Exception("DataArrayInt::fromLinkedListOfPairToList : no tuples in this ! Not a linked list !");
6821 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(nbTuples+1,1);
6822 const int *thisPtr(begin());
6823 int *retPtr(ret->getPointer());
6824 retPtr[0]=thisPtr[0];
6825 for(int i=0;i<nbTuples;i++)
6827 retPtr[i+1]=thisPtr[2*i+1];
6829 if(thisPtr[2*i+1]!=thisPtr[2*(i+1)+0])
6831 std::ostringstream oss; oss << "DataArrayInt::fromLinkedListOfPairToList : this is not a proper linked list of pair. The link is broken between tuple #" << i << " and tuple #" << i+1 << " ! Call sortEachPairToMakeALinkedList ?";
6832 throw INTERP_KERNEL::Exception(oss.str());
6839 * This method returns all different values found in \a this. This method throws if \a this has not been allocated.
6840 * But the number of components can be different from one.
6841 * \return a newly allocated array (that should be dealt by the caller) containing different values in \a this.
6843 DataArrayInt *DataArrayInt::getDifferentValues() const
6847 ret.insert(begin(),end());
6848 MCAuto<DataArrayInt> ret2=DataArrayInt::New(); ret2->alloc((int)ret.size(),1);
6849 std::copy(ret.begin(),ret.end(),ret2->getPointer());
6854 * This method is a refinement of DataArrayInt::getDifferentValues because it returns not only different values in \a this but also, for each of
6855 * them it tells which tuple id have this id.
6856 * This method works only on arrays with one component (if it is not the case call DataArrayInt::rearrange(1) ).
6857 * This method returns two arrays having same size.
6858 * The instances of DataArrayInt in the returned vector have be specially allocated and computed by this method. Each of them should be dealt by the caller of this method.
6859 * Example : if this is equal to [1,0,1,2,0,2,2,-3,2] -> differentIds=[-3,0,1,2] and returned array will be equal to [[7],[1,4],[0,2],[3,5,6,8]]
6861 std::vector<DataArrayInt *> DataArrayInt::partitionByDifferentValues(std::vector<int>& differentIds) const
6864 if(getNumberOfComponents()!=1)
6865 throw INTERP_KERNEL::Exception("DataArrayInt::partitionByDifferentValues : this should have only one component !");
6867 std::map<int,int> m,m2,m3;
6868 for(const int *w=begin();w!=end();w++)
6870 differentIds.resize(m.size());
6871 std::vector<DataArrayInt *> ret(m.size());
6872 std::vector<int *> retPtr(m.size());
6873 for(std::map<int,int>::const_iterator it=m.begin();it!=m.end();it++,id++)
6876 ret[id]=DataArrayInt::New();
6877 ret[id]->alloc((*it).second,1);
6878 retPtr[id]=ret[id]->getPointer();
6879 differentIds[id]=(*it).first;
6882 for(const int *w=begin();w!=end();w++,id++)
6884 retPtr[m2[*w]][m3[*w]++]=id;
6890 * This method split ids in [0, \c this->getNumberOfTuples() ) using \a this array as a field of weight (>=0 each).
6891 * The aim of this method is to return a set of \a nbOfSlices chunk of contiguous ids as balanced as possible.
6893 * \param [in] nbOfSlices - number of slices expected.
6894 * \return - a vector having a size equal to \a nbOfSlices giving the start (included) and the stop (excluded) of each chunks.
6896 * \sa DataArray::GetSlice
6897 * \throw If \a this is not allocated or not with exactly one component.
6898 * \throw If an element in \a this if < 0.
6900 std::vector< std::pair<int,int> > DataArrayInt::splitInBalancedSlices(int nbOfSlices) const
6902 if(!isAllocated() || getNumberOfComponents()!=1)
6903 throw INTERP_KERNEL::Exception("DataArrayInt::splitInBalancedSlices : this array should have number of components equal to one and must be allocated !");
6905 throw INTERP_KERNEL::Exception("DataArrayInt::splitInBalancedSlices : number of slices must be >= 1 !");
6906 int sum(accumulate(0)),nbOfTuples(getNumberOfTuples());
6907 int sumPerSlc(sum/nbOfSlices),pos(0);
6908 const int *w(begin());
6909 std::vector< std::pair<int,int> > ret(nbOfSlices);
6910 for(int i=0;i<nbOfSlices;i++)
6912 std::pair<int,int> p(pos,-1);
6914 while(locSum<sumPerSlc && pos<nbOfTuples) { pos++; locSum+=*w++; }
6918 p.second=nbOfTuples;
6925 * Returns a new DataArrayInt that is a modulus of two given arrays. There are 3
6927 * 1. The arrays have same number of tuples and components. Then each value of
6928 * the result array (_a_) is a division of the corresponding values of \a a1 and
6929 * \a a2, i.e.: _a_ [ i, j ] = _a1_ [ i, j ] % _a2_ [ i, j ].
6930 * 2. The arrays have same number of tuples and one array, say _a2_, has one
6932 * _a_ [ i, j ] = _a1_ [ i, j ] % _a2_ [ i, 0 ].
6933 * 3. The arrays have same number of components and one array, say _a2_, has one
6935 * _a_ [ i, j ] = _a1_ [ i, j ] % _a2_ [ 0, j ].
6937 * Info on components is copied either from the first array (in the first case) or from
6938 * the array with maximal number of elements (getNbOfElems()).
6939 * \warning No check of division by zero is performed!
6940 * \param [in] a1 - a dividend array.
6941 * \param [in] a2 - a divisor array.
6942 * \return DataArrayInt * - the new instance of DataArrayInt.
6943 * The caller is to delete this result array using decrRef() as it is no more
6945 * \throw If either \a a1 or \a a2 is NULL.
6946 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
6947 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
6948 * none of them has number of tuples or components equal to 1.
6950 DataArrayInt *DataArrayInt::Modulus(const DataArrayInt *a1, const DataArrayInt *a2)
6953 throw INTERP_KERNEL::Exception("DataArrayInt::Modulus : input DataArrayInt instance is NULL !");
6954 int nbOfTuple1=a1->getNumberOfTuples();
6955 int nbOfTuple2=a2->getNumberOfTuples();
6956 int nbOfComp1=a1->getNumberOfComponents();
6957 int nbOfComp2=a2->getNumberOfComponents();
6958 if(nbOfTuple2==nbOfTuple1)
6960 if(nbOfComp1==nbOfComp2)
6962 MCAuto<DataArrayInt> ret=DataArrayInt::New();
6963 ret->alloc(nbOfTuple2,nbOfComp1);
6964 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::modulus<int>());
6965 ret->copyStringInfoFrom(*a1);
6968 else if(nbOfComp2==1)
6970 MCAuto<DataArrayInt> ret=DataArrayInt::New();
6971 ret->alloc(nbOfTuple1,nbOfComp1);
6972 const int *a2Ptr=a2->getConstPointer();
6973 const int *a1Ptr=a1->getConstPointer();
6974 int *res=ret->getPointer();
6975 for(int i=0;i<nbOfTuple1;i++)
6976 res=std::transform(a1Ptr+i*nbOfComp1,a1Ptr+(i+1)*nbOfComp1,res,std::bind2nd(std::modulus<int>(),a2Ptr[i]));
6977 ret->copyStringInfoFrom(*a1);
6982 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Modulus !");
6986 else if(nbOfTuple2==1)
6988 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Modulus !");
6989 MCAuto<DataArrayInt> ret=DataArrayInt::New();
6990 ret->alloc(nbOfTuple1,nbOfComp1);
6991 const int *a1ptr=a1->getConstPointer(),*a2ptr=a2->getConstPointer();
6992 int *pt=ret->getPointer();
6993 for(int i=0;i<nbOfTuple1;i++)
6994 pt=std::transform(a1ptr+i*nbOfComp1,a1ptr+(i+1)*nbOfComp1,a2ptr,pt,std::modulus<int>());
6995 ret->copyStringInfoFrom(*a1);
7000 a1->checkNbOfTuples(nbOfTuple2,"Nb of tuples mismatch for array Modulus !");//will always throw an exception
7006 * Modify \a this array so that each value becomes a modulus of division of this value by
7007 * a value of another DataArrayInt. There are 3 valid cases.
7008 * 1. The arrays have same number of tuples and components. Then each value of
7009 * \a this array is divided by the corresponding value of \a other one, i.e.:
7010 * _a_ [ i, j ] %= _other_ [ i, j ].
7011 * 2. The arrays have same number of tuples and \a other array has one component. Then
7012 * _a_ [ i, j ] %= _other_ [ i, 0 ].
7013 * 3. The arrays have same number of components and \a other array has one tuple. Then
7014 * _a_ [ i, j ] %= _a2_ [ 0, j ].
7016 * \warning No check of division by zero is performed!
7017 * \param [in] other - a divisor array.
7018 * \throw If \a other is NULL.
7019 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
7020 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
7021 * \a other has number of both tuples and components not equal to 1.
7023 void DataArrayInt::modulusEqual(const DataArrayInt *other)
7026 throw INTERP_KERNEL::Exception("DataArrayInt::modulusEqual : input DataArrayInt instance is NULL !");
7027 const char *msg="Nb of tuples mismatch for DataArrayInt::modulusEqual !";
7028 checkAllocated(); other->checkAllocated();
7029 int nbOfTuple=getNumberOfTuples();
7030 int nbOfTuple2=other->getNumberOfTuples();
7031 int nbOfComp=getNumberOfComponents();
7032 int nbOfComp2=other->getNumberOfComponents();
7033 if(nbOfTuple==nbOfTuple2)
7035 if(nbOfComp==nbOfComp2)
7037 std::transform(begin(),end(),other->begin(),getPointer(),std::modulus<int>());
7039 else if(nbOfComp2==1)
7041 if(nbOfComp2==nbOfComp)
7043 int *ptr=getPointer();
7044 const int *ptrc=other->getConstPointer();
7045 for(int i=0;i<nbOfTuple;i++)
7046 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::modulus<int>(),*ptrc++));
7049 throw INTERP_KERNEL::Exception(msg);
7052 throw INTERP_KERNEL::Exception(msg);
7054 else if(nbOfTuple2==1)
7056 int *ptr=getPointer();
7057 const int *ptrc=other->getConstPointer();
7058 for(int i=0;i<nbOfTuple;i++)
7059 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::modulus<int>());
7062 throw INTERP_KERNEL::Exception(msg);
7067 * Returns a new DataArrayInt that is the result of pow of two given arrays. There are 3
7070 * \param [in] a1 - an array to pow up.
7071 * \param [in] a2 - another array to sum up.
7072 * \return DataArrayInt * - the new instance of DataArrayInt.
7073 * The caller is to delete this result array using decrRef() as it is no more
7075 * \throw If either \a a1 or \a a2 is NULL.
7076 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
7077 * \throw If \a a1->getNumberOfComponents() != 1 or \a a2->getNumberOfComponents() != 1.
7078 * \throw If there is a negative value in \a a2.
7080 DataArrayInt *DataArrayInt::Pow(const DataArrayInt *a1, const DataArrayInt *a2)
7083 throw INTERP_KERNEL::Exception("DataArrayInt::Pow : at least one of input instances is null !");
7084 int nbOfTuple=a1->getNumberOfTuples();
7085 int nbOfTuple2=a2->getNumberOfTuples();
7086 int nbOfComp=a1->getNumberOfComponents();
7087 int nbOfComp2=a2->getNumberOfComponents();
7088 if(nbOfTuple!=nbOfTuple2)
7089 throw INTERP_KERNEL::Exception("DataArrayInt::Pow : number of tuples mismatches !");
7090 if(nbOfComp!=1 || nbOfComp2!=1)
7091 throw INTERP_KERNEL::Exception("DataArrayInt::Pow : number of components of both arrays must be equal to 1 !");
7092 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbOfTuple,1);
7093 const int *ptr1(a1->begin()),*ptr2(a2->begin());
7094 int *ptr=ret->getPointer();
7095 for(int i=0;i<nbOfTuple;i++,ptr1++,ptr2++,ptr++)
7100 for(int j=0;j<*ptr2;j++)
7106 std::ostringstream oss; oss << "DataArrayInt::Pow : on tuple #" << i << " of a2 value is < 0 (" << *ptr2 << ") !";
7107 throw INTERP_KERNEL::Exception(oss.str().c_str());
7114 * Apply pow on values of another DataArrayInt to values of \a this one.
7116 * \param [in] other - an array to pow to \a this one.
7117 * \throw If \a other is NULL.
7118 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples()
7119 * \throw If \a this->getNumberOfComponents() != 1 or \a other->getNumberOfComponents() != 1
7120 * \throw If there is a negative value in \a other.
7122 void DataArrayInt::powEqual(const DataArrayInt *other)
7125 throw INTERP_KERNEL::Exception("DataArrayInt::powEqual : input instance is null !");
7126 int nbOfTuple=getNumberOfTuples();
7127 int nbOfTuple2=other->getNumberOfTuples();
7128 int nbOfComp=getNumberOfComponents();
7129 int nbOfComp2=other->getNumberOfComponents();
7130 if(nbOfTuple!=nbOfTuple2)
7131 throw INTERP_KERNEL::Exception("DataArrayInt::powEqual : number of tuples mismatches !");
7132 if(nbOfComp!=1 || nbOfComp2!=1)
7133 throw INTERP_KERNEL::Exception("DataArrayInt::powEqual : number of components of both arrays must be equal to 1 !");
7134 int *ptr=getPointer();
7135 const int *ptrc=other->begin();
7136 for(int i=0;i<nbOfTuple;i++,ptrc++,ptr++)
7141 for(int j=0;j<*ptrc;j++)
7147 std::ostringstream oss; oss << "DataArrayInt::powEqual : on tuple #" << i << " of other value is < 0 (" << *ptrc << ") !";
7148 throw INTERP_KERNEL::Exception(oss.str().c_str());
7155 * Returns a C array which is a renumbering map in "Old to New" mode for the input array.
7156 * This map, if applied to \a start array, would make it sorted. For example, if
7157 * \a start array contents are [9,10,0,6,4,11,3,7] then the contents of the result array is
7158 * [5,6,0,3,2,7,1,4].
7159 * \param [in] start - pointer to the first element of the array for which the
7160 * permutation map is computed.
7161 * \param [in] end - pointer specifying the end of the array \a start, so that
7162 * the last value of \a start is \a end[ -1 ].
7163 * \return int * - the result permutation array that the caller is to delete as it is no
7165 * \throw If there are equal values in the input array.
7167 int *DataArrayInt::CheckAndPreparePermutation(const int *start, const int *end)
7169 std::size_t sz=std::distance(start,end);
7170 int *ret=(int *)malloc(sz*sizeof(int));
7171 int *work=new int[sz];
7172 std::copy(start,end,work);
7173 std::sort(work,work+sz);
7174 if(std::unique(work,work+sz)!=work+sz)
7178 throw INTERP_KERNEL::Exception("Some elements are equals in the specified array !");
7180 std::map<int,int> m;
7181 for(int *workPt=work;workPt!=work+sz;workPt++)
7182 m[*workPt]=(int)std::distance(work,workPt);
7184 for(const int *iter=start;iter!=end;iter++,iter2++)
7191 * Returns a new DataArrayInt containing an arithmetic progression
7192 * that is equal to the sequence returned by Python \c range(\a begin,\a end,\a step )
7194 * \param [in] begin - the start value of the result sequence.
7195 * \param [in] end - limiting value, so that every value of the result array is less than
7197 * \param [in] step - specifies the increment or decrement.
7198 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
7199 * array using decrRef() as it is no more needed.
7200 * \throw If \a step == 0.
7201 * \throw If \a end < \a begin && \a step > 0.
7202 * \throw If \a end > \a begin && \a step < 0.
7204 DataArrayInt *DataArrayInt::Range(int begin, int end, int step)
7206 int nbOfTuples=GetNumberOfItemGivenBESRelative(begin,end,step,"DataArrayInt::Range");
7207 MCAuto<DataArrayInt> ret=DataArrayInt::New();
7208 ret->alloc(nbOfTuples,1);
7209 int *ptr=ret->getPointer();
7212 for(int i=begin;i<end;i+=step,ptr++)
7217 for(int i=begin;i>end;i+=step,ptr++)
7224 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
7227 void DataArrayInt::getTinySerializationIntInformation(std::vector<int>& tinyInfo) const
7232 tinyInfo[0]=getNumberOfTuples();
7233 tinyInfo[1]=getNumberOfComponents();
7243 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
7246 void DataArrayInt::getTinySerializationStrInformation(std::vector<std::string>& tinyInfo) const
7250 int nbOfCompo=getNumberOfComponents();
7251 tinyInfo.resize(nbOfCompo+1);
7252 tinyInfo[0]=getName();
7253 for(int i=0;i<nbOfCompo;i++)
7254 tinyInfo[i+1]=getInfoOnComponent(i);
7259 tinyInfo[0]=getName();
7264 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
7265 * This method returns if a feeding is needed.
7267 bool DataArrayInt::resizeForUnserialization(const std::vector<int>& tinyInfoI)
7269 int nbOfTuple=tinyInfoI[0];
7270 int nbOfComp=tinyInfoI[1];
7271 if(nbOfTuple!=-1 || nbOfComp!=-1)
7273 alloc(nbOfTuple,nbOfComp);
7280 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
7281 * This method returns if a feeding is needed.
7283 void DataArrayInt::finishUnserialization(const std::vector<int>& tinyInfoI, const std::vector<std::string>& tinyInfoS)
7285 setName(tinyInfoS[0]);
7288 int nbOfCompo=tinyInfoI[1];
7289 for(int i=0;i<nbOfCompo;i++)
7290 setInfoOnComponent(i,tinyInfoS[i+1]);
7294 DataArrayIntIterator::DataArrayIntIterator(DataArrayInt *da):DataArrayIterator<int>(da)
7298 DataArrayIntTuple::DataArrayIntTuple(int *pt, int nbOfComp):DataArrayTuple<int>(pt,nbOfComp)
7302 std::string DataArrayIntTuple::repr() const
7304 std::ostringstream oss; oss << "(";
7305 for(int i=0;i<_nb_of_compo-1;i++)
7306 oss << _pt[i] << ", ";
7307 oss << _pt[_nb_of_compo-1] << ")";
7311 int DataArrayIntTuple::intValue() const
7313 return this->zeValue();
7317 * This method returns a newly allocated instance the caller should dealed with by a MEDCoupling::DataArrayInt::decrRef.
7318 * This method performs \b no copy of data. The content is only referenced using MEDCoupling::DataArrayInt::useArray with ownership set to \b false.
7319 * This method throws an INTERP_KERNEL::Exception is it is impossible to match sizes of \b this that is too say \b nbOfCompo=this->_nb_of_elem and \bnbOfTuples==1 or
7320 * \b nbOfCompo=1 and \bnbOfTuples==this->_nb_of_elem.
7322 DataArrayInt *DataArrayIntTuple::buildDAInt(int nbOfTuples, int nbOfCompo) const
7324 return this->buildDA(nbOfTuples,nbOfCompo);