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>;
48 template<int SPACEDIM>
49 void DataArrayDouble::findCommonTuplesAlg(const double *bbox, int nbNodes, int limitNodeId, double prec, DataArrayInt *c, DataArrayInt *cI) const
51 const double *coordsPtr=getConstPointer();
52 BBTreePts<SPACEDIM,int> myTree(bbox,0,0,nbNodes,prec);
53 std::vector<bool> isDone(nbNodes);
54 for(int i=0;i<nbNodes;i++)
58 std::vector<int> intersectingElems;
59 myTree.getElementsAroundPoint(coordsPtr+i*SPACEDIM,intersectingElems);
60 if(intersectingElems.size()>1)
62 std::vector<int> commonNodes;
63 for(std::vector<int>::const_iterator it=intersectingElems.begin();it!=intersectingElems.end();it++)
67 commonNodes.push_back(*it);
70 if(!commonNodes.empty())
72 cI->pushBackSilent(cI->back()+(int)commonNodes.size()+1);
74 c->insertAtTheEnd(commonNodes.begin(),commonNodes.end());
81 template<int SPACEDIM>
82 void DataArrayDouble::FindTupleIdsNearTuplesAlg(const BBTreePts<SPACEDIM,int>& myTree, const double *pos, int nbOfTuples, double eps,
83 DataArrayInt *c, DataArrayInt *cI)
85 for(int i=0;i<nbOfTuples;i++)
87 std::vector<int> intersectingElems;
88 myTree.getElementsAroundPoint(pos+i*SPACEDIM,intersectingElems);
89 std::vector<int> commonNodes;
90 for(std::vector<int>::const_iterator it=intersectingElems.begin();it!=intersectingElems.end();it++)
91 commonNodes.push_back(*it);
92 cI->pushBackSilent(cI->back()+(int)commonNodes.size());
93 c->insertAtTheEnd(commonNodes.begin(),commonNodes.end());
97 template<int SPACEDIM>
98 void DataArrayDouble::FindClosestTupleIdAlg(const BBTreePts<SPACEDIM,int>& myTree, double dist, const double *pos, int nbOfTuples, const double *thisPt, int thisNbOfTuples, int *res)
100 double distOpt(dist);
101 const double *p(pos);
103 for(int i=0;i<nbOfTuples;i++,p+=SPACEDIM,r++)
108 double ret=myTree.getElementsAroundPoint2(p,distOpt,elem);
109 if(ret!=std::numeric_limits<double>::max())
111 distOpt=std::max(ret,1e-4);
116 { distOpt=2*distOpt; continue; }
121 int DataArray::EffectiveCircPerm(int nbOfShift, int nbOfTuples)
124 throw INTERP_KERNEL::Exception("DataArray::EffectiveCircPerm : number of tuples is expected to be > 0 !");
127 return nbOfShift%nbOfTuples;
133 return nbOfTuples-tmp;
137 std::size_t DataArray::getHeapMemorySizeWithoutChildren() const
139 std::size_t sz1=_name.capacity();
140 std::size_t sz2=_info_on_compo.capacity();
142 for(std::vector<std::string>::const_iterator it=_info_on_compo.begin();it!=_info_on_compo.end();it++)
143 sz3+=(*it).capacity();
147 std::vector<const BigMemoryObject *> DataArray::getDirectChildrenWithNull() const
149 return std::vector<const BigMemoryObject *>();
153 * Sets the attribute \a _name of \a this array.
154 * See \ref MEDCouplingArrayBasicsName "DataArrays infos" for more information.
155 * \param [in] name - new array name
157 void DataArray::setName(const std::string& name)
163 * Copies textual data from an \a other DataArray. The copied data are
164 * - the name attribute,
165 * - the information of components.
167 * For more information on these data see \ref MEDCouplingArrayBasicsName "DataArrays infos".
169 * \param [in] other - another instance of DataArray to copy the textual data from.
170 * \throw If number of components of \a this array differs from that of the \a other.
172 void DataArray::copyStringInfoFrom(const DataArray& other)
174 if(_info_on_compo.size()!=other._info_on_compo.size())
175 throw INTERP_KERNEL::Exception("Size of arrays mismatches on copyStringInfoFrom !");
177 _info_on_compo=other._info_on_compo;
180 void DataArray::copyPartOfStringInfoFrom(const DataArray& other, const std::vector<int>& compoIds)
182 int nbOfCompoOth=other.getNumberOfComponents();
183 std::size_t newNbOfCompo=compoIds.size();
184 for(std::size_t i=0;i<newNbOfCompo;i++)
185 if(compoIds[i]>=nbOfCompoOth || compoIds[i]<0)
187 std::ostringstream oss; oss << "Specified component id is out of range (" << compoIds[i] << ") compared with nb of actual components (" << nbOfCompoOth << ")";
188 throw INTERP_KERNEL::Exception(oss.str().c_str());
190 for(std::size_t i=0;i<newNbOfCompo;i++)
191 setInfoOnComponent((int)i,other.getInfoOnComponent(compoIds[i]));
194 void DataArray::copyPartOfStringInfoFrom2(const std::vector<int>& compoIds, const DataArray& other)
196 int nbOfCompo=getNumberOfComponents();
197 std::size_t partOfCompoToSet=compoIds.size();
198 if((int)partOfCompoToSet!=other.getNumberOfComponents())
199 throw INTERP_KERNEL::Exception("Given compoIds has not the same size as number of components of given array !");
200 for(std::size_t i=0;i<partOfCompoToSet;i++)
201 if(compoIds[i]>=nbOfCompo || compoIds[i]<0)
203 std::ostringstream oss; oss << "Specified component id is out of range (" << compoIds[i] << ") compared with nb of actual components (" << nbOfCompo << ")";
204 throw INTERP_KERNEL::Exception(oss.str().c_str());
206 for(std::size_t i=0;i<partOfCompoToSet;i++)
207 setInfoOnComponent(compoIds[i],other.getInfoOnComponent((int)i));
210 bool DataArray::areInfoEqualsIfNotWhy(const DataArray& other, std::string& reason) const
212 std::ostringstream oss;
213 if(_name!=other._name)
215 oss << "Names DataArray mismatch : this name=\"" << _name << " other name=\"" << other._name << "\" !";
219 if(_info_on_compo!=other._info_on_compo)
221 oss << "Components DataArray mismatch : \nThis components=";
222 for(std::vector<std::string>::const_iterator it=_info_on_compo.begin();it!=_info_on_compo.end();it++)
223 oss << "\"" << *it << "\",";
224 oss << "\nOther components=";
225 for(std::vector<std::string>::const_iterator it=other._info_on_compo.begin();it!=other._info_on_compo.end();it++)
226 oss << "\"" << *it << "\",";
234 * Compares textual information of \a this DataArray with that of an \a other one.
235 * The compared data are
236 * - the name attribute,
237 * - the information of components.
239 * For more information on these data see \ref MEDCouplingArrayBasicsName "DataArrays infos".
240 * \param [in] other - another instance of DataArray to compare the textual data of.
241 * \return bool - \a true if the textual information is same, \a false else.
243 bool DataArray::areInfoEquals(const DataArray& other) const
246 return areInfoEqualsIfNotWhy(other,tmp);
249 void DataArray::reprWithoutNameStream(std::ostream& stream) const
251 stream << "Number of components : "<< getNumberOfComponents() << "\n";
252 stream << "Info of these components : ";
253 for(std::vector<std::string>::const_iterator iter=_info_on_compo.begin();iter!=_info_on_compo.end();iter++)
254 stream << "\"" << *iter << "\" ";
258 std::string DataArray::cppRepr(const std::string& varName) const
260 std::ostringstream ret;
261 reprCppStream(varName,ret);
266 * Sets information on all components. To know more on format of this information
267 * see \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
268 * \param [in] info - a vector of strings.
269 * \throw If size of \a info differs from the number of components of \a this.
271 void DataArray::setInfoOnComponents(const std::vector<std::string>& info)
273 if(getNumberOfComponents()!=(int)info.size())
275 std::ostringstream oss; oss << "DataArray::setInfoOnComponents : input is of size " << info.size() << " whereas number of components is equal to " << getNumberOfComponents() << " !";
276 throw INTERP_KERNEL::Exception(oss.str().c_str());
282 * This method is only a dispatcher towards DataArrayDouble::setPartOfValues3, DataArrayInt::setPartOfValues3, DataArrayChar::setPartOfValues3 depending on the true
283 * type of \a this and \a aBase.
285 * \throw If \a aBase and \a this do not have the same type.
287 * \sa DataArrayDouble::setPartOfValues3, DataArrayInt::setPartOfValues3, DataArrayChar::setPartOfValues3.
289 void DataArray::setPartOfValuesBase3(const DataArray *aBase, const int *bgTuples, const int *endTuples, int bgComp, int endComp, int stepComp, bool strictCompoCompare)
292 throw INTERP_KERNEL::Exception("DataArray::setPartOfValuesBase3 : input aBase object is NULL !");
293 DataArrayDouble *this1(dynamic_cast<DataArrayDouble *>(this));
294 DataArrayInt *this2(dynamic_cast<DataArrayInt *>(this));
295 DataArrayChar *this3(dynamic_cast<DataArrayChar *>(this));
296 const DataArrayDouble *a1(dynamic_cast<const DataArrayDouble *>(aBase));
297 const DataArrayInt *a2(dynamic_cast<const DataArrayInt *>(aBase));
298 const DataArrayChar *a3(dynamic_cast<const DataArrayChar *>(aBase));
301 this1->setPartOfValues3(a1,bgTuples,endTuples,bgComp,endComp,stepComp,strictCompoCompare);
306 this2->setPartOfValues3(a2,bgTuples,endTuples,bgComp,endComp,stepComp,strictCompoCompare);
311 this3->setPartOfValues3(a3,bgTuples,endTuples,bgComp,endComp,stepComp,strictCompoCompare);
314 throw INTERP_KERNEL::Exception("DataArray::setPartOfValuesBase3 : input aBase object and this do not have the same type !");
317 std::vector<std::string> DataArray::getVarsOnComponent() const
319 int nbOfCompo=(int)_info_on_compo.size();
320 std::vector<std::string> ret(nbOfCompo);
321 for(int i=0;i<nbOfCompo;i++)
322 ret[i]=getVarOnComponent(i);
326 std::vector<std::string> DataArray::getUnitsOnComponent() const
328 int nbOfCompo=(int)_info_on_compo.size();
329 std::vector<std::string> ret(nbOfCompo);
330 for(int i=0;i<nbOfCompo;i++)
331 ret[i]=getUnitOnComponent(i);
336 * Returns information on a component specified by an index.
337 * To know more on format of this information
338 * see \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
339 * \param [in] i - the index (zero based) of the component of interest.
340 * \return std::string - a string containing the information on \a i-th component.
341 * \throw If \a i is not a valid component index.
343 std::string DataArray::getInfoOnComponent(int i) const
345 if(i<(int)_info_on_compo.size() && i>=0)
346 return _info_on_compo[i];
349 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();
350 throw INTERP_KERNEL::Exception(oss.str().c_str());
355 * Returns the var part of the full information of the \a i-th component.
356 * For example, if \c getInfoOnComponent(0) returns "SIGXY [N/m^2]", then
357 * \c getVarOnComponent(0) returns "SIGXY".
358 * If a unit part of information is not detected by presence of
359 * two square brackets, then the full information is returned.
360 * To read more about the component information format, see
361 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
362 * \param [in] i - the index (zero based) of the component of interest.
363 * \return std::string - a string containing the var information, or the full info.
364 * \throw If \a i is not a valid component index.
366 std::string DataArray::getVarOnComponent(int i) const
368 if(i<(int)_info_on_compo.size() && i>=0)
370 return GetVarNameFromInfo(_info_on_compo[i]);
374 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();
375 throw INTERP_KERNEL::Exception(oss.str().c_str());
380 * Returns the unit part of the full information of the \a i-th component.
381 * For example, if \c getInfoOnComponent(0) returns "SIGXY [ N/m^2]", then
382 * \c getUnitOnComponent(0) returns " N/m^2".
383 * If a unit part of information is not detected by presence of
384 * two square brackets, then an empty string is returned.
385 * To read more about the component information format, see
386 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
387 * \param [in] i - the index (zero based) of the component of interest.
388 * \return std::string - a string containing the unit information, if any, or "".
389 * \throw If \a i is not a valid component index.
391 std::string DataArray::getUnitOnComponent(int i) const
393 if(i<(int)_info_on_compo.size() && i>=0)
395 return GetUnitFromInfo(_info_on_compo[i]);
399 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();
400 throw INTERP_KERNEL::Exception(oss.str().c_str());
405 * Returns the var part of the full component information.
406 * For example, if \a info == "SIGXY [N/m^2]", then this method returns "SIGXY".
407 * If a unit part of information is not detected by presence of
408 * two square brackets, then the whole \a info is returned.
409 * To read more about the component information format, see
410 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
411 * \param [in] info - the full component information.
412 * \return std::string - a string containing only var information, or the \a info.
414 std::string DataArray::GetVarNameFromInfo(const std::string& info)
416 std::size_t p1=info.find_last_of('[');
417 std::size_t p2=info.find_last_of(']');
418 if(p1==std::string::npos || p2==std::string::npos)
423 return std::string();
424 std::size_t p3=info.find_last_not_of(' ',p1-1);
425 return info.substr(0,p3+1);
429 * Returns the unit part of the full component information.
430 * For example, if \a info == "SIGXY [ N/m^2]", then this method returns " N/m^2".
431 * If a unit part of information is not detected by presence of
432 * two square brackets, then an empty string is returned.
433 * To read more about the component information format, see
434 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
435 * \param [in] info - the full component information.
436 * \return std::string - a string containing only unit information, if any, or "".
438 std::string DataArray::GetUnitFromInfo(const std::string& info)
440 std::size_t p1=info.find_last_of('[');
441 std::size_t p2=info.find_last_of(']');
442 if(p1==std::string::npos || p2==std::string::npos)
443 return std::string();
445 return std::string();
446 return info.substr(p1+1,p2-p1-1);
450 * This method put in info format the result of the merge of \a var and \a unit.
451 * The standard format for that is "var [unit]".
452 * Inversely you can retrieve the var part or the unit part of info string using resp. GetVarNameFromInfo and GetUnitFromInfo.
454 std::string DataArray::BuildInfoFromVarAndUnit(const std::string& var, const std::string& unit)
456 std::ostringstream oss;
457 oss << var << " [" << unit << "]";
461 std::string DataArray::GetAxisTypeRepr(MEDCouplingAxisType at)
466 return std::string("AX_CART");
468 return std::string("AX_CYL");
470 return std::string("AX_SPHER");
472 throw INTERP_KERNEL::Exception("DataArray::GetAxisTypeRepr : unrecognized axis type enum !");
477 * Returns a new DataArray by concatenating all given arrays, so that (1) the number
478 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
479 * the number of component in the result array is same as that of each of given arrays.
480 * Info on components is copied from the first of the given arrays. Number of components
481 * in the given arrays must be the same.
482 * \param [in] arrs - a sequence of arrays to include in the result array. All arrays must have the same type.
483 * \return DataArray * - the new instance of DataArray (that can be either DataArrayInt, DataArrayDouble, DataArrayChar).
484 * The caller is to delete this result array using decrRef() as it is no more
486 * \throw If all arrays within \a arrs are NULL.
487 * \throw If all not null arrays in \a arrs have not the same type.
488 * \throw If getNumberOfComponents() of arrays within \a arrs.
490 DataArray *DataArray::Aggregate(const std::vector<const DataArray *>& arrs)
492 std::vector<const DataArray *> arr2;
493 for(std::vector<const DataArray *>::const_iterator it=arrs.begin();it!=arrs.end();it++)
497 throw INTERP_KERNEL::Exception("DataArray::Aggregate : only null instance in input vector !");
498 std::vector<const DataArrayDouble *> arrd;
499 std::vector<const DataArrayInt *> arri;
500 std::vector<const DataArrayChar *> arrc;
501 for(std::vector<const DataArray *>::const_iterator it=arr2.begin();it!=arr2.end();it++)
503 const DataArrayDouble *a=dynamic_cast<const DataArrayDouble *>(*it);
505 { arrd.push_back(a); continue; }
506 const DataArrayInt *b=dynamic_cast<const DataArrayInt *>(*it);
508 { arri.push_back(b); continue; }
509 const DataArrayChar *c=dynamic_cast<const DataArrayChar *>(*it);
511 { arrc.push_back(c); continue; }
512 throw INTERP_KERNEL::Exception("DataArray::Aggregate : presence of not null instance in inuput that is not in [DataArrayDouble, DataArrayInt, DataArrayChar] !");
514 if(arr2.size()==arrd.size())
515 return DataArrayDouble::Aggregate(arrd);
516 if(arr2.size()==arri.size())
517 return DataArrayInt::Aggregate(arri);
518 if(arr2.size()==arrc.size())
519 return DataArrayChar::Aggregate(arrc);
520 throw INTERP_KERNEL::Exception("DataArray::Aggregate : all input arrays must have the same type !");
524 * Sets information on a component specified by an index.
525 * To know more on format of this information
526 * see \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
527 * \warning Don't pass NULL as \a info!
528 * \param [in] i - the index (zero based) of the component of interest.
529 * \param [in] info - the string containing the information.
530 * \throw If \a i is not a valid component index.
532 void DataArray::setInfoOnComponent(int i, const std::string& info)
534 if(i<(int)_info_on_compo.size() && i>=0)
535 _info_on_compo[i]=info;
538 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();
539 throw INTERP_KERNEL::Exception(oss.str().c_str());
544 * Sets information on all components. This method can change number of components
545 * at certain conditions; if the conditions are not respected, an exception is thrown.
546 * The number of components can be changed in \a this only if \a this is not allocated.
547 * The condition of number of components must not be changed.
549 * To know more on format of the component information see
550 * \ref MEDCouplingArrayBasicsCompoName "DataArrays infos".
551 * \param [in] info - a vector of component infos.
552 * \throw If \a this->getNumberOfComponents() != \a info.size() && \a this->isAllocated()
554 void DataArray::setInfoAndChangeNbOfCompo(const std::vector<std::string>& info)
556 if(getNumberOfComponents()!=(int)info.size())
562 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 !";
563 throw INTERP_KERNEL::Exception(oss.str().c_str());
570 void DataArray::checkNbOfTuples(int nbOfTuples, const std::string& msg) const
572 if(getNumberOfTuples()!=nbOfTuples)
574 std::ostringstream oss; oss << msg << " : mismatch number of tuples : expected " << nbOfTuples << " having " << getNumberOfTuples() << " !";
575 throw INTERP_KERNEL::Exception(oss.str().c_str());
579 void DataArray::checkNbOfComps(int nbOfCompo, const std::string& msg) const
581 if(getNumberOfComponents()!=nbOfCompo)
583 std::ostringstream oss; oss << msg << " : mismatch number of components : expected " << nbOfCompo << " having " << getNumberOfComponents() << " !";
584 throw INTERP_KERNEL::Exception(oss.str().c_str());
588 void DataArray::checkNbOfElems(std::size_t nbOfElems, const std::string& msg) const
590 if(getNbOfElems()!=nbOfElems)
592 std::ostringstream oss; oss << msg << " : mismatch number of elems : Expected " << nbOfElems << " having " << getNbOfElems() << " !";
593 throw INTERP_KERNEL::Exception(oss.str().c_str());
597 void DataArray::checkNbOfTuplesAndComp(const DataArray& other, const std::string& msg) const
599 if(getNumberOfTuples()!=other.getNumberOfTuples())
601 std::ostringstream oss; oss << msg << " : mismatch number of tuples : expected " << other.getNumberOfTuples() << " having " << getNumberOfTuples() << " !";
602 throw INTERP_KERNEL::Exception(oss.str().c_str());
604 if(getNumberOfComponents()!=other.getNumberOfComponents())
606 std::ostringstream oss; oss << msg << " : mismatch number of components : expected " << other.getNumberOfComponents() << " having " << getNumberOfComponents() << " !";
607 throw INTERP_KERNEL::Exception(oss.str().c_str());
611 void DataArray::checkNbOfTuplesAndComp(int nbOfTuples, int nbOfCompo, const std::string& msg) const
613 checkNbOfTuples(nbOfTuples,msg);
614 checkNbOfComps(nbOfCompo,msg);
618 * Simply this method checks that \b value is in [0,\b ref).
620 void DataArray::CheckValueInRange(int ref, int value, const std::string& msg)
622 if(value<0 || value>=ref)
624 std::ostringstream oss; oss << "DataArray::CheckValueInRange : " << msg << " ! Expected in range [0," << ref << "[ having " << value << " !";
625 throw INTERP_KERNEL::Exception(oss.str().c_str());
630 * This method checks that [\b start, \b end) is compliant with ref length \b value.
631 * typicaly start in [0,\b value) and end in [0,\b value). If value==start and start==end, it is supported.
633 void DataArray::CheckValueInRangeEx(int value, int start, int end, const std::string& msg)
635 if(start<0 || start>=value)
637 if(value!=start || end!=start)
639 std::ostringstream oss; oss << "DataArray::CheckValueInRangeEx : " << msg << " ! Expected start " << start << " of input range, in [0," << value << "[ !";
640 throw INTERP_KERNEL::Exception(oss.str().c_str());
643 if(end<0 || end>value)
645 std::ostringstream oss; oss << "DataArray::CheckValueInRangeEx : " << msg << " ! Expected end " << end << " of input range, in [0," << value << "] !";
646 throw INTERP_KERNEL::Exception(oss.str().c_str());
650 void DataArray::CheckClosingParInRange(int ref, int value, const std::string& msg)
652 if(value<0 || value>ref)
654 std::ostringstream oss; oss << "DataArray::CheckClosingParInRange : " << msg << " ! Expected input range in [0," << ref << "] having closing open parenthesis " << value << " !";
655 throw INTERP_KERNEL::Exception(oss.str().c_str());
660 * 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,
661 * typically it is a whole slice of tuples of DataArray or cells, nodes of a mesh...
663 * The input \a sliceId should be an id in [0, \a nbOfSlices) that specifies the slice of work.
665 * \param [in] start - the start of the input slice of the whole work to perform splitted into slices.
666 * \param [in] stop - the stop of the input slice of the whole work to perform splitted into slices.
667 * \param [in] step - the step (that can be <0) of the input slice of the whole work to perform splitted into slices.
668 * \param [in] sliceId - the slice id considered
669 * \param [in] nbOfSlices - the number of slices (typically the number of cores on which the work is expected to be sliced)
670 * \param [out] startSlice - the start of the slice considered
671 * \param [out] stopSlice - the stop of the slice consided
673 * \throw If \a step == 0
674 * \throw If \a nbOfSlices not > 0
675 * \throw If \a sliceId not in [0,nbOfSlices)
677 void DataArray::GetSlice(int start, int stop, int step, int sliceId, int nbOfSlices, int& startSlice, int& stopSlice)
681 std::ostringstream oss; oss << "DataArray::GetSlice : nbOfSlices (" << nbOfSlices << ") must be > 0 !";
682 throw INTERP_KERNEL::Exception(oss.str().c_str());
684 if(sliceId<0 || sliceId>=nbOfSlices)
686 std::ostringstream oss; oss << "DataArray::GetSlice : sliceId (" << nbOfSlices << ") must be in [0 , nbOfSlices (" << nbOfSlices << ") ) !";
687 throw INTERP_KERNEL::Exception(oss.str().c_str());
689 int nbElems=GetNumberOfItemGivenBESRelative(start,stop,step,"DataArray::GetSlice");
690 int minNbOfElemsPerSlice=nbElems/nbOfSlices;
691 startSlice=start+minNbOfElemsPerSlice*step*sliceId;
692 if(sliceId<nbOfSlices-1)
693 stopSlice=start+minNbOfElemsPerSlice*step*(sliceId+1);
698 int DataArray::GetNumberOfItemGivenBES(int begin, int end, int step, const std::string& msg)
702 std::ostringstream oss; oss << msg << " : end before begin !";
703 throw INTERP_KERNEL::Exception(oss.str().c_str());
709 std::ostringstream oss; oss << msg << " : invalid step should be > 0 !";
710 throw INTERP_KERNEL::Exception(oss.str().c_str());
712 return (end-1-begin)/step+1;
715 int DataArray::GetNumberOfItemGivenBESRelative(int begin, int end, int step, const std::string& msg)
718 throw INTERP_KERNEL::Exception("DataArray::GetNumberOfItemGivenBES : step=0 is not allowed !");
719 if(end<begin && step>0)
721 std::ostringstream oss; oss << msg << " : end before begin whereas step is positive !";
722 throw INTERP_KERNEL::Exception(oss.str().c_str());
724 if(begin<end && step<0)
726 std::ostringstream oss; oss << msg << " : invalid step should be > 0 !";
727 throw INTERP_KERNEL::Exception(oss.str().c_str());
730 return (std::max(begin,end)-1-std::min(begin,end))/std::abs(step)+1;
735 int DataArray::GetPosOfItemGivenBESRelativeNoThrow(int value, int begin, int end, int step)
741 if(begin<=value && value<end)
743 if((value-begin)%step==0)
744 return (value-begin)/step;
753 if(begin>=value && value>end)
755 if((begin-value)%(-step)==0)
756 return (begin-value)/(-step);
769 * Returns a new instance of DataArrayDouble. The caller is to delete this array
770 * using decrRef() as it is no more needed.
772 DataArrayDouble *DataArrayDouble::New()
774 return new DataArrayDouble;
778 * Returns the only one value in \a this, if and only if number of elements
779 * (nb of tuples * nb of components) is equal to 1, and that \a this is allocated.
780 * \return double - the sole value stored in \a this array.
781 * \throw If at least one of conditions stated above is not fulfilled.
783 double DataArrayDouble::doubleValue() const
787 if(getNbOfElems()==1)
789 return *getConstPointer();
792 throw INTERP_KERNEL::Exception("DataArrayDouble::doubleValue : DataArrayDouble instance is allocated but number of elements is not equal to 1 !");
795 throw INTERP_KERNEL::Exception("DataArrayDouble::doubleValue : DataArrayDouble instance is not allocated !");
799 * Returns a full copy of \a this. For more info on copying data arrays see
800 * \ref MEDCouplingArrayBasicsCopyDeep.
801 * \return DataArrayDouble * - a new instance of DataArrayDouble. The caller is to
802 * delete this array using decrRef() as it is no more needed.
804 DataArrayDouble *DataArrayDouble::deepCopy() const
806 return new DataArrayDouble(*this);
810 * Returns either a \a deep or \a shallow copy of this array. For more info see
811 * \ref MEDCouplingArrayBasicsCopyDeep and \ref MEDCouplingArrayBasicsCopyShallow.
812 * \param [in] dCpy - if \a true, a deep copy is returned, else, a shallow one.
813 * \return DataArrayDouble * - either a new instance of DataArrayDouble (if \a dCpy
814 * == \a true) or \a this instance (if \a dCpy == \a false).
816 DataArrayDouble *DataArrayDouble::performCopyOrIncrRef(bool dCpy) const
818 return DataArrayTemplateClassic<double>::PerformCopyOrIncrRef(dCpy,*this);
822 * Assign zero to all values in \a this array. To know more on filling arrays see
823 * \ref MEDCouplingArrayFill.
824 * \throw If \a this is not allocated.
826 void DataArrayDouble::fillWithZero()
832 * Checks that \a this array is consistently **increasing** or **decreasing** in value,
833 * with at least absolute difference value of |\a eps| at each step.
834 * If not an exception is thrown.
835 * \param [in] increasing - if \a true, the array values should be increasing.
836 * \param [in] eps - minimal absolute difference between the neighbor values at which
837 * the values are considered different.
838 * \throw If sequence of values is not strictly monotonic in agreement with \a
840 * \throw If \a this->getNumberOfComponents() != 1.
841 * \throw If \a this is not allocated.
843 void DataArrayDouble::checkMonotonic(bool increasing, double eps) const
845 if(!isMonotonic(increasing,eps))
848 throw INTERP_KERNEL::Exception("DataArrayDouble::checkMonotonic : 'this' is not INCREASING monotonic !");
850 throw INTERP_KERNEL::Exception("DataArrayDouble::checkMonotonic : 'this' is not DECREASING monotonic !");
855 * Checks that \a this array is consistently **increasing** or **decreasing** in value,
856 * with at least absolute difference value of |\a eps| at each step.
857 * \param [in] increasing - if \a true, array values should be increasing.
858 * \param [in] eps - minimal absolute difference between the neighbor values at which
859 * the values are considered different.
860 * \return bool - \a true if values change in accordance with \a increasing arg.
861 * \throw If \a this->getNumberOfComponents() != 1.
862 * \throw If \a this is not allocated.
864 bool DataArrayDouble::isMonotonic(bool increasing, double eps) const
867 if(getNumberOfComponents()!=1)
868 throw INTERP_KERNEL::Exception("DataArrayDouble::isMonotonic : only supported with 'this' array with ONE component !");
869 int nbOfElements=getNumberOfTuples();
870 const double *ptr=getConstPointer();
874 double absEps=fabs(eps);
877 for(int i=1;i<nbOfElements;i++)
879 if(ptr[i]<(ref+absEps))
887 for(int i=1;i<nbOfElements;i++)
889 if(ptr[i]>(ref-absEps))
898 * Returns a textual and human readable representation of \a this instance of
899 * DataArrayDouble. This text is shown when a DataArrayDouble is printed in Python.
900 * \return std::string - text describing \a this DataArrayDouble.
902 * \sa reprNotTooLong, reprZip
904 std::string DataArrayDouble::repr() const
906 std::ostringstream ret;
911 std::string DataArrayDouble::reprZip() const
913 std::ostringstream ret;
919 * This method is close to repr method except that when \a this has more than 1000 tuples, all tuples are not
920 * printed out to avoid to consume too much space in interpretor.
923 std::string DataArrayDouble::reprNotTooLong() const
925 std::ostringstream ret;
926 reprNotTooLongStream(ret);
930 void DataArrayDouble::writeVTK(std::ostream& ofs, int indent, const std::string& nameInFile, DataArrayByte *byteArr) const
932 static const char SPACE[4]={' ',' ',' ',' '};
934 std::string idt(indent,' ');
936 ofs << idt << "<DataArray type=\"Float32\" Name=\"" << nameInFile << "\" NumberOfComponents=\"" << getNumberOfComponents() << "\"";
938 bool areAllEmpty(true);
939 for(std::vector<std::string>::const_iterator it=_info_on_compo.begin();it!=_info_on_compo.end();it++)
943 for(std::size_t i=0;i<_info_on_compo.size();i++)
944 ofs << " ComponentName" << i << "=\"" << _info_on_compo[i] << "\"";
948 ofs << " format=\"appended\" offset=\"" << byteArr->getNumberOfTuples() << "\">";
949 INTERP_KERNEL::AutoPtr<float> tmp(new float[getNbOfElems()]);
951 // to make Visual C++ happy : instead of std::copy(begin(),end(),(float *)tmp);
952 for(const double *src=begin();src!=end();src++,pt++)
954 const char *data(reinterpret_cast<const char *>((float *)tmp));
955 std::size_t sz(getNbOfElems()*sizeof(float));
956 byteArr->insertAtTheEnd(data,data+sz);
957 byteArr->insertAtTheEnd(SPACE,SPACE+4);
961 ofs << " RangeMin=\"" << getMinValueInArray() << "\" RangeMax=\"" << getMaxValueInArray() << "\" format=\"ascii\">\n" << idt;
962 std::copy(begin(),end(),std::ostream_iterator<double>(ofs," "));
964 ofs << std::endl << idt << "</DataArray>\n";
967 void DataArrayDouble::reprStream(std::ostream& stream) const
969 stream << "Name of double array : \"" << _name << "\"\n";
970 reprWithoutNameStream(stream);
973 void DataArrayDouble::reprZipStream(std::ostream& stream) const
975 stream << "Name of double array : \"" << _name << "\"\n";
976 reprZipWithoutNameStream(stream);
979 void DataArrayDouble::reprNotTooLongStream(std::ostream& stream) const
981 stream << "Name of double array : \"" << _name << "\"\n";
982 reprNotTooLongWithoutNameStream(stream);
985 void DataArrayDouble::reprWithoutNameStream(std::ostream& stream) const
987 DataArray::reprWithoutNameStream(stream);
988 stream.precision(17);
989 _mem.repr(getNumberOfComponents(),stream);
992 void DataArrayDouble::reprZipWithoutNameStream(std::ostream& stream) const
994 DataArray::reprWithoutNameStream(stream);
995 stream.precision(17);
996 _mem.reprZip(getNumberOfComponents(),stream);
999 void DataArrayDouble::reprNotTooLongWithoutNameStream(std::ostream& stream) const
1001 DataArray::reprWithoutNameStream(stream);
1002 stream.precision(17);
1003 _mem.reprNotTooLong(getNumberOfComponents(),stream);
1006 void DataArrayDouble::reprCppStream(const std::string& varName, std::ostream& stream) const
1008 int nbTuples(getNumberOfTuples()),nbComp(getNumberOfComponents());
1009 const double *data(getConstPointer());
1010 stream.precision(17);
1011 stream << "DataArrayDouble *" << varName << "=DataArrayDouble::New();" << std::endl;
1012 if(nbTuples*nbComp>=1)
1014 stream << "const double " << varName << "Data[" << nbTuples*nbComp << "]={";
1015 std::copy(data,data+nbTuples*nbComp-1,std::ostream_iterator<double>(stream,","));
1016 stream << data[nbTuples*nbComp-1] << "};" << std::endl;
1017 stream << varName << "->useArray(" << varName << "Data,false,CPP_DEALLOC," << nbTuples << "," << nbComp << ");" << std::endl;
1020 stream << varName << "->alloc(" << nbTuples << "," << nbComp << ");" << std::endl;
1021 stream << varName << "->setName(\"" << getName() << "\");" << std::endl;
1025 * Method that gives a quick overvien of \a this for python.
1027 void DataArrayDouble::reprQuickOverview(std::ostream& stream) const
1029 static const std::size_t MAX_NB_OF_BYTE_IN_REPR=300;
1030 stream << "DataArrayDouble C++ instance at " << this << ". ";
1033 int nbOfCompo=(int)_info_on_compo.size();
1036 int nbOfTuples=getNumberOfTuples();
1037 stream << "Number of tuples : " << nbOfTuples << ". Number of components : " << nbOfCompo << "." << std::endl;
1038 reprQuickOverviewData(stream,MAX_NB_OF_BYTE_IN_REPR);
1041 stream << "Number of components : 0.";
1044 stream << "*** No data allocated ****";
1047 void DataArrayDouble::reprQuickOverviewData(std::ostream& stream, std::size_t maxNbOfByteInRepr) const
1049 const double *data=begin();
1050 int nbOfTuples=getNumberOfTuples();
1051 int nbOfCompo=(int)_info_on_compo.size();
1052 std::ostringstream oss2; oss2 << "[";
1054 std::string oss2Str(oss2.str());
1055 bool isFinished=true;
1056 for(int i=0;i<nbOfTuples && isFinished;i++)
1061 for(int j=0;j<nbOfCompo;j++,data++)
1064 if(j!=nbOfCompo-1) oss2 << ", ";
1070 if(i!=nbOfTuples-1) oss2 << ", ";
1071 std::string oss3Str(oss2.str());
1072 if(oss3Str.length()<maxNbOfByteInRepr)
1084 * Equivalent to DataArrayDouble::isEqual except that if false the reason of
1085 * mismatch is given.
1087 * \param [in] other the instance to be compared with \a this
1088 * \param [in] prec the precision to compare numeric data of the arrays.
1089 * \param [out] reason In case of inequality returns the reason.
1090 * \sa DataArrayDouble::isEqual
1092 bool DataArrayDouble::isEqualIfNotWhy(const DataArrayDouble& other, double prec, std::string& reason) const
1094 if(!areInfoEqualsIfNotWhy(other,reason))
1096 return _mem.isEqual(other._mem,prec,reason);
1100 * Checks if \a this and another DataArrayDouble are fully equal. For more info see
1101 * \ref MEDCouplingArrayBasicsCompare.
1102 * \param [in] other - an instance of DataArrayDouble to compare with \a this one.
1103 * \param [in] prec - precision value to compare numeric data of the arrays.
1104 * \return bool - \a true if the two arrays are equal, \a false else.
1106 bool DataArrayDouble::isEqual(const DataArrayDouble& other, double prec) const
1109 return isEqualIfNotWhy(other,prec,tmp);
1113 * Checks if values of \a this and another DataArrayDouble are equal. For more info see
1114 * \ref MEDCouplingArrayBasicsCompare.
1115 * \param [in] other - an instance of DataArrayDouble to compare with \a this one.
1116 * \param [in] prec - precision value to compare numeric data of the arrays.
1117 * \return bool - \a true if the values of two arrays are equal, \a false else.
1119 bool DataArrayDouble::isEqualWithoutConsideringStr(const DataArrayDouble& other, double prec) const
1122 return _mem.isEqual(other._mem,prec,tmp);
1126 * Returns a new DataArrayDouble holding the same values as \a this array but differently
1127 * arranged in memory. If \a this array holds 2 components of 3 values:
1128 * \f$ x_0,x_1,x_2,y_0,y_1,y_2 \f$, then the result array holds these values arranged
1129 * as follows: \f$ x_0,y_0,x_1,y_1,x_2,y_2 \f$.
1130 * \warning Do not confuse this method with transpose()!
1131 * \return DataArrayDouble * - the new instance of DataArrayDouble that the caller
1132 * is to delete using decrRef() as it is no more needed.
1133 * \throw If \a this is not allocated.
1135 DataArrayDouble *DataArrayDouble::fromNoInterlace() const
1138 throw INTERP_KERNEL::Exception("DataArrayDouble::fromNoInterlace : Not defined array !");
1139 double *tab=_mem.fromNoInterlace(getNumberOfComponents());
1140 DataArrayDouble *ret=DataArrayDouble::New();
1141 ret->useArray(tab,true,C_DEALLOC,getNumberOfTuples(),getNumberOfComponents());
1146 * Returns a new DataArrayDouble holding the same values as \a this array but differently
1147 * arranged in memory. If \a this array holds 2 components of 3 values:
1148 * \f$ x_0,y_0,x_1,y_1,x_2,y_2 \f$, then the result array holds these values arranged
1149 * as follows: \f$ x_0,x_1,x_2,y_0,y_1,y_2 \f$.
1150 * \warning Do not confuse this method with transpose()!
1151 * \return DataArrayDouble * - the new instance of DataArrayDouble that the caller
1152 * is to delete using decrRef() as it is no more needed.
1153 * \throw If \a this is not allocated.
1155 DataArrayDouble *DataArrayDouble::toNoInterlace() const
1158 throw INTERP_KERNEL::Exception("DataArrayDouble::toNoInterlace : Not defined array !");
1159 double *tab=_mem.toNoInterlace(getNumberOfComponents());
1160 DataArrayDouble *ret=DataArrayDouble::New();
1161 ret->useArray(tab,true,C_DEALLOC,getNumberOfTuples(),getNumberOfComponents());
1166 * Appends components of another array to components of \a this one, tuple by tuple.
1167 * So that the number of tuples of \a this array remains the same and the number of
1168 * components increases.
1169 * \param [in] other - the DataArrayDouble to append to \a this one.
1170 * \throw If \a this is not allocated.
1171 * \throw If \a this and \a other arrays have different number of tuples.
1173 * \if ENABLE_EXAMPLES
1174 * \ref cpp_mcdataarraydouble_meldwith "Here is a C++ example".
1176 * \ref py_mcdataarraydouble_meldwith "Here is a Python example".
1179 void DataArrayDouble::meldWith(const DataArrayDouble *other)
1182 other->checkAllocated();
1183 int nbOfTuples=getNumberOfTuples();
1184 if(nbOfTuples!=other->getNumberOfTuples())
1185 throw INTERP_KERNEL::Exception("DataArrayDouble::meldWith : mismatch of number of tuples !");
1186 int nbOfComp1=getNumberOfComponents();
1187 int nbOfComp2=other->getNumberOfComponents();
1188 double *newArr=(double *)malloc((nbOfTuples*(nbOfComp1+nbOfComp2))*sizeof(double));
1190 const double *inp1=getConstPointer();
1191 const double *inp2=other->getConstPointer();
1192 for(int i=0;i<nbOfTuples;i++,inp1+=nbOfComp1,inp2+=nbOfComp2)
1194 w=std::copy(inp1,inp1+nbOfComp1,w);
1195 w=std::copy(inp2,inp2+nbOfComp2,w);
1197 useArray(newArr,true,C_DEALLOC,nbOfTuples,nbOfComp1+nbOfComp2);
1198 std::vector<int> compIds(nbOfComp2);
1199 for(int i=0;i<nbOfComp2;i++)
1200 compIds[i]=nbOfComp1+i;
1201 copyPartOfStringInfoFrom2(compIds,*other);
1205 * This method checks that all tuples in \a other are in \a this.
1206 * If true, the output param \a tupleIds contains the tuples ids of \a this that correspond to tupes in \a this.
1207 * 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.
1209 * \param [in] other - the array having the same number of components than \a this.
1210 * \param [out] tupleIds - the tuple ids containing the same number of tuples than \a other has.
1211 * \sa DataArrayDouble::findCommonTuples
1213 bool DataArrayDouble::areIncludedInMe(const DataArrayDouble *other, double prec, DataArrayInt *&tupleIds) const
1216 throw INTERP_KERNEL::Exception("DataArrayDouble::areIncludedInMe : input array is NULL !");
1217 checkAllocated(); other->checkAllocated();
1218 if(getNumberOfComponents()!=other->getNumberOfComponents())
1219 throw INTERP_KERNEL::Exception("DataArrayDouble::areIncludedInMe : the number of components does not match !");
1220 MCAuto<DataArrayDouble> a=DataArrayDouble::Aggregate(this,other);
1221 DataArrayInt *c=0,*ci=0;
1222 a->findCommonTuples(prec,getNumberOfTuples(),c,ci);
1223 MCAuto<DataArrayInt> cSafe(c),ciSafe(ci);
1224 int newNbOfTuples=-1;
1225 MCAuto<DataArrayInt> ids=DataArrayInt::ConvertIndexArrayToO2N(a->getNumberOfTuples(),c->begin(),ci->begin(),ci->end(),newNbOfTuples);
1226 MCAuto<DataArrayInt> ret1=ids->selectByTupleIdSafeSlice(getNumberOfTuples(),a->getNumberOfTuples(),1);
1227 tupleIds=ret1.retn();
1228 return newNbOfTuples==getNumberOfTuples();
1232 * Searches for tuples coincident within \a prec tolerance. Each tuple is considered
1233 * as coordinates of a point in getNumberOfComponents()-dimensional space. The
1234 * distance separating two points is computed with the infinite norm.
1236 * Indices of coincident tuples are stored in output arrays.
1237 * A pair of arrays (\a comm, \a commIndex) is called "Surjective Format 2".
1239 * This method is typically used by MEDCouplingPointSet::findCommonNodes() and
1240 * MEDCouplingUMesh::mergeNodes().
1241 * \param [in] prec - minimal absolute distance between two tuples (infinite norm) at which they are
1242 * considered not coincident.
1243 * \param [in] limitTupleId - limit tuple id. If all tuples within a group of coincident
1244 * tuples have id strictly lower than \a limitTupleId then they are not returned.
1245 * \param [out] comm - the array holding ids (== indices) of coincident tuples.
1246 * \a comm->getNumberOfComponents() == 1.
1247 * \a comm->getNumberOfTuples() == \a commIndex->back().
1248 * \param [out] commIndex - the array dividing all indices stored in \a comm into
1249 * groups of (indices of) coincident tuples. Its every value is a tuple
1250 * index where a next group of tuples begins. For example the second
1251 * group of tuples in \a comm is described by following range of indices:
1252 * [ \a commIndex[1], \a commIndex[2] ). \a commIndex->getNumberOfTuples()-1
1253 * gives the number of groups of coincident tuples.
1254 * \throw If \a this is not allocated.
1255 * \throw If the number of components is not in [1,2,3,4].
1257 * \if ENABLE_EXAMPLES
1258 * \ref cpp_mcdataarraydouble_findcommontuples "Here is a C++ example".
1260 * \ref py_mcdataarraydouble_findcommontuples "Here is a Python example".
1262 * \sa DataArrayInt::ConvertIndexArrayToO2N(), DataArrayDouble::areIncludedInMe
1264 void DataArrayDouble::findCommonTuples(double prec, int limitTupleId, DataArrayInt *&comm, DataArrayInt *&commIndex) const
1267 int nbOfCompo=getNumberOfComponents();
1268 if ((nbOfCompo<1) || (nbOfCompo>4)) //test before work
1269 throw INTERP_KERNEL::Exception("DataArrayDouble::findCommonTuples : Unexpected spacedim of coords. Must be 1, 2, 3 or 4.");
1271 int nbOfTuples=getNumberOfTuples();
1273 MCAuto<DataArrayInt> c(DataArrayInt::New()),cI(DataArrayInt::New()); c->alloc(0,1); cI->pushBackSilent(0);
1277 findCommonTuplesAlg<4>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1280 findCommonTuplesAlg<3>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1283 findCommonTuplesAlg<2>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1286 findCommonTuplesAlg<1>(begin(),nbOfTuples,limitTupleId,prec,c,cI);
1289 throw INTERP_KERNEL::Exception("DataArrayDouble::findCommonTuples : nb of components managed are 1,2,3 and 4 ! not implemented for other number of components !");
1292 commIndex=cI.retn();
1297 * \param [in] nbTimes specifies the nb of times each tuples in \a this will be duplicated contiguouly in returned DataArrayDouble instance.
1298 * \a nbTimes should be at least equal to 1.
1299 * \return a newly allocated DataArrayDouble having one component and number of tuples equal to \a nbTimes * \c this->getNumberOfTuples.
1300 * \throw if \a this is not allocated or if \a this has not number of components set to one or if \a nbTimes is lower than 1.
1302 DataArrayDouble *DataArrayDouble::duplicateEachTupleNTimes(int nbTimes) const
1305 if(getNumberOfComponents()!=1)
1306 throw INTERP_KERNEL::Exception("DataArrayDouble::duplicateEachTupleNTimes : this should have only one component !");
1308 throw INTERP_KERNEL::Exception("DataArrayDouble::duplicateEachTupleNTimes : nb times should be >= 1 !");
1309 int nbTuples=getNumberOfTuples();
1310 const double *inPtr=getConstPointer();
1311 MCAuto<DataArrayDouble> ret=DataArrayDouble::New(); ret->alloc(nbTimes*nbTuples,1);
1312 double *retPtr=ret->getPointer();
1313 for(int i=0;i<nbTuples;i++,inPtr++)
1316 for(int j=0;j<nbTimes;j++,retPtr++)
1319 ret->copyStringInfoFrom(*this);
1324 * This methods returns the minimal distance between the two set of points \a this and \a other.
1325 * So \a this and \a other have to have the same number of components. If not an INTERP_KERNEL::Exception will be thrown.
1326 * This method works only if number of components of \a this (equal to those of \a other) is in 1, 2 or 3.
1328 * \param [out] thisTupleId the tuple id in \a this corresponding to the returned minimal distance
1329 * \param [out] otherTupleId the tuple id in \a other corresponding to the returned minimal distance
1330 * \return the minimal distance between the two set of points \a this and \a other.
1331 * \sa DataArrayDouble::findClosestTupleId
1333 double DataArrayDouble::minimalDistanceTo(const DataArrayDouble *other, int& thisTupleId, int& otherTupleId) const
1335 MCAuto<DataArrayInt> part1=findClosestTupleId(other);
1336 int nbOfCompo(getNumberOfComponents());
1337 int otherNbTuples(other->getNumberOfTuples());
1338 const double *thisPt(begin()),*otherPt(other->begin());
1339 const int *part1Pt(part1->begin());
1340 double ret=std::numeric_limits<double>::max();
1341 for(int i=0;i<otherNbTuples;i++,part1Pt++,otherPt+=nbOfCompo)
1344 for(int j=0;j<nbOfCompo;j++)
1345 tmp+=(otherPt[j]-thisPt[nbOfCompo*(*part1Pt)+j])*(otherPt[j]-thisPt[nbOfCompo*(*part1Pt)+j]);
1347 { ret=tmp; thisTupleId=*part1Pt; otherTupleId=i; }
1353 * This methods returns for each tuple in \a other which tuple in \a this is the closest.
1354 * So \a this and \a other have to have the same number of components. If not an INTERP_KERNEL::Exception will be thrown.
1355 * This method works only if number of components of \a this (equal to those of \a other) is in 1, 2 or 3.
1357 * \return a newly allocated (new object to be dealt by the caller) DataArrayInt having \c other->getNumberOfTuples() tuples and one components.
1358 * \sa DataArrayDouble::minimalDistanceTo
1360 DataArrayInt *DataArrayDouble::findClosestTupleId(const DataArrayDouble *other) const
1363 throw INTERP_KERNEL::Exception("DataArrayDouble::findClosestTupleId : other instance is NULL !");
1364 checkAllocated(); other->checkAllocated();
1365 int nbOfCompo=getNumberOfComponents();
1366 if(nbOfCompo!=other->getNumberOfComponents())
1368 std::ostringstream oss; oss << "DataArrayDouble::findClosestTupleId : number of components in this is " << nbOfCompo;
1369 oss << ", whereas number of components in other is " << other->getNumberOfComponents() << "! Should be equal !";
1370 throw INTERP_KERNEL::Exception(oss.str().c_str());
1372 int nbOfTuples=other->getNumberOfTuples();
1373 int thisNbOfTuples=getNumberOfTuples();
1374 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbOfTuples,1);
1376 getMinMaxPerComponent(bounds);
1381 double xDelta(fabs(bounds[1]-bounds[0])),yDelta(fabs(bounds[3]-bounds[2])),zDelta(fabs(bounds[5]-bounds[4]));
1382 double delta=std::max(xDelta,yDelta); delta=std::max(delta,zDelta);
1383 double characSize=pow((delta*delta*delta)/((double)thisNbOfTuples),1./3.);
1384 BBTreePts<3,int> myTree(begin(),0,0,getNumberOfTuples(),characSize*1e-12);
1385 FindClosestTupleIdAlg<3>(myTree,3.*characSize*characSize,other->begin(),nbOfTuples,begin(),thisNbOfTuples,ret->getPointer());
1390 double xDelta(fabs(bounds[1]-bounds[0])),yDelta(fabs(bounds[3]-bounds[2]));
1391 double delta=std::max(xDelta,yDelta);
1392 double characSize=sqrt(delta/(double)thisNbOfTuples);
1393 BBTreePts<2,int> myTree(begin(),0,0,getNumberOfTuples(),characSize*1e-12);
1394 FindClosestTupleIdAlg<2>(myTree,2.*characSize*characSize,other->begin(),nbOfTuples,begin(),thisNbOfTuples,ret->getPointer());
1399 double characSize=fabs(bounds[1]-bounds[0])/thisNbOfTuples;
1400 BBTreePts<1,int> myTree(begin(),0,0,getNumberOfTuples(),characSize*1e-12);
1401 FindClosestTupleIdAlg<1>(myTree,1.*characSize*characSize,other->begin(),nbOfTuples,begin(),thisNbOfTuples,ret->getPointer());
1405 throw INTERP_KERNEL::Exception("Unexpected spacedim of coords for findClosestTupleId. Must be 1, 2 or 3.");
1411 * This method expects that \a this and \a otherBBoxFrmt arrays are bounding box arrays ( as the output of MEDCouplingPointSet::getBoundingBoxForBBTree method ).
1412 * 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
1413 * how many bounding boxes in \a otherBBoxFrmt.
1414 * So, this method expects that \a this and \a otherBBoxFrmt have the same number of components.
1416 * \param [in] otherBBoxFrmt - It is an array .
1417 * \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.
1418 * \sa MEDCouplingPointSet::getBoundingBoxForBBTree
1419 * \throw If \a this and \a otherBBoxFrmt have not the same number of components.
1420 * \throw If \a this and \a otherBBoxFrmt number of components is not even (BBox format).
1422 DataArrayInt *DataArrayDouble::computeNbOfInteractionsWith(const DataArrayDouble *otherBBoxFrmt, double eps) const
1425 throw INTERP_KERNEL::Exception("DataArrayDouble::computeNbOfInteractionsWith : input array is NULL !");
1426 if(!isAllocated() || !otherBBoxFrmt->isAllocated())
1427 throw INTERP_KERNEL::Exception("DataArrayDouble::computeNbOfInteractionsWith : this and input array must be allocated !");
1428 int nbOfComp(getNumberOfComponents()),nbOfTuples(getNumberOfTuples());
1429 if(nbOfComp!=otherBBoxFrmt->getNumberOfComponents())
1431 std::ostringstream oss; oss << "DataArrayDouble::computeNbOfInteractionsWith : this number of components (" << nbOfComp << ") must be equal to the number of components of input array (" << otherBBoxFrmt->getNumberOfComponents() << ") !";
1432 throw INTERP_KERNEL::Exception(oss.str().c_str());
1436 std::ostringstream oss; oss << "DataArrayDouble::computeNbOfInteractionsWith : Number of components (" << nbOfComp << ") is not even ! It should be to be compatible with bbox format !";
1437 throw INTERP_KERNEL::Exception(oss.str().c_str());
1439 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(nbOfTuples,1);
1440 const double *thisBBPtr(begin());
1441 int *retPtr(ret->getPointer());
1446 BBTree<3,int> bbt(otherBBoxFrmt->begin(),0,0,otherBBoxFrmt->getNumberOfTuples(),eps);
1447 for(int i=0;i<nbOfTuples;i++,retPtr++,thisBBPtr+=nbOfComp)
1448 *retPtr=bbt.getNbOfIntersectingElems(thisBBPtr);
1453 BBTree<2,int> bbt(otherBBoxFrmt->begin(),0,0,otherBBoxFrmt->getNumberOfTuples(),eps);
1454 for(int i=0;i<nbOfTuples;i++,retPtr++,thisBBPtr+=nbOfComp)
1455 *retPtr=bbt.getNbOfIntersectingElems(thisBBPtr);
1460 BBTree<1,int> bbt(otherBBoxFrmt->begin(),0,0,otherBBoxFrmt->getNumberOfTuples(),eps);
1461 for(int i=0;i<nbOfTuples;i++,retPtr++,thisBBPtr+=nbOfComp)
1462 *retPtr=bbt.getNbOfIntersectingElems(thisBBPtr);
1466 throw INTERP_KERNEL::Exception("DataArrayDouble::computeNbOfInteractionsWith : space dimension supported are [1,2,3] !");
1473 * Returns a copy of \a this array by excluding coincident tuples. Each tuple is
1474 * considered as coordinates of a point in getNumberOfComponents()-dimensional
1475 * space. The distance between tuples is computed using norm2. If several tuples are
1476 * not far each from other than \a prec, only one of them remains in the result
1477 * array. The order of tuples in the result array is same as in \a this one except
1478 * that coincident tuples are excluded.
1479 * \param [in] prec - minimal absolute distance between two tuples at which they are
1480 * considered not coincident.
1481 * \param [in] limitTupleId - limit tuple id. If all tuples within a group of coincident
1482 * tuples have id strictly lower than \a limitTupleId then they are not excluded.
1483 * \return DataArrayDouble * - the new instance of DataArrayDouble that the caller
1484 * is to delete using decrRef() as it is no more needed.
1485 * \throw If \a this is not allocated.
1486 * \throw If the number of components is not in [1,2,3,4].
1488 * \if ENABLE_EXAMPLES
1489 * \ref py_mcdataarraydouble_getdifferentvalues "Here is a Python example".
1492 DataArrayDouble *DataArrayDouble::getDifferentValues(double prec, int limitTupleId) const
1495 DataArrayInt *c0=0,*cI0=0;
1496 findCommonTuples(prec,limitTupleId,c0,cI0);
1497 MCAuto<DataArrayInt> c(c0),cI(cI0);
1498 int newNbOfTuples=-1;
1499 MCAuto<DataArrayInt> o2n=DataArrayInt::ConvertIndexArrayToO2N(getNumberOfTuples(),c0->begin(),cI0->begin(),cI0->end(),newNbOfTuples);
1500 return renumberAndReduce(o2n->getConstPointer(),newNbOfTuples);
1504 * Copy all components in a specified order from another DataArrayDouble.
1505 * Both numerical and textual data is copied. The number of tuples in \a this and
1506 * the other array can be different.
1507 * \param [in] a - the array to copy data from.
1508 * \param [in] compoIds - sequence of zero based indices of components, data of which is
1510 * \throw If \a a is NULL.
1511 * \throw If \a compoIds.size() != \a a->getNumberOfComponents().
1512 * \throw If \a compoIds[i] < 0 or \a compoIds[i] > \a this->getNumberOfComponents().
1514 * \if ENABLE_EXAMPLES
1515 * \ref py_mcdataarraydouble_setselectedcomponents "Here is a Python example".
1518 void DataArrayDouble::setSelectedComponents(const DataArrayDouble *a, const std::vector<int>& compoIds)
1521 throw INTERP_KERNEL::Exception("DataArrayDouble::setSelectedComponents : input DataArrayDouble is NULL !");
1523 copyPartOfStringInfoFrom2(compoIds,*a);
1524 std::size_t partOfCompoSz=compoIds.size();
1525 int nbOfCompo=getNumberOfComponents();
1526 int nbOfTuples=std::min(getNumberOfTuples(),a->getNumberOfTuples());
1527 const double *ac=a->getConstPointer();
1528 double *nc=getPointer();
1529 for(int i=0;i<nbOfTuples;i++)
1530 for(std::size_t j=0;j<partOfCompoSz;j++,ac++)
1531 nc[nbOfCompo*i+compoIds[j]]=*ac;
1534 void DataArrayDouble::SetArrayIn(DataArrayDouble *newArray, DataArrayDouble* &arrayToSet)
1536 if(newArray!=arrayToSet)
1539 arrayToSet->decrRef();
1540 arrayToSet=newArray;
1542 arrayToSet->incrRef();
1546 void DataArrayDouble::aggregate(const DataArrayDouble *other)
1549 throw INTERP_KERNEL::Exception("DataArrayDouble::aggregate : null pointer !");
1550 if(getNumberOfComponents()!=other->getNumberOfComponents())
1551 throw INTERP_KERNEL::Exception("DataArrayDouble::aggregate : mismatch number of components !");
1552 _mem.insertAtTheEnd(other->begin(),other->end());
1556 * Checks if 0.0 value is present in \a this array. If it is the case, an exception
1558 * \throw If zero is found in \a this array.
1560 void DataArrayDouble::checkNoNullValues() const
1562 const double *tmp=getConstPointer();
1563 std::size_t nbOfElems=getNbOfElems();
1564 const double *where=std::find(tmp,tmp+nbOfElems,0.);
1565 if(where!=tmp+nbOfElems)
1566 throw INTERP_KERNEL::Exception("A value 0.0 have been detected !");
1570 * Computes minimal and maximal value in each component. An output array is filled
1571 * with \c 2 * \a this->getNumberOfComponents() values, so the caller is to allocate
1572 * enough memory before calling this method.
1573 * \param [out] bounds - array of size at least 2 *\a this->getNumberOfComponents().
1574 * It is filled as follows:<br>
1575 * \a bounds[0] = \c min_of_component_0 <br>
1576 * \a bounds[1] = \c max_of_component_0 <br>
1577 * \a bounds[2] = \c min_of_component_1 <br>
1578 * \a bounds[3] = \c max_of_component_1 <br>
1581 void DataArrayDouble::getMinMaxPerComponent(double *bounds) const
1584 int dim=getNumberOfComponents();
1585 for (int idim=0; idim<dim; idim++)
1587 bounds[idim*2]=std::numeric_limits<double>::max();
1588 bounds[idim*2+1]=-std::numeric_limits<double>::max();
1590 const double *ptr=getConstPointer();
1591 int nbOfTuples=getNumberOfTuples();
1592 for(int i=0;i<nbOfTuples;i++)
1594 for(int idim=0;idim<dim;idim++)
1596 if(bounds[idim*2]>ptr[i*dim+idim])
1598 bounds[idim*2]=ptr[i*dim+idim];
1600 if(bounds[idim*2+1]<ptr[i*dim+idim])
1602 bounds[idim*2+1]=ptr[i*dim+idim];
1609 * This method retrieves a newly allocated DataArrayDouble instance having same number of tuples than \a this and twice number of components than \a this
1610 * to store both the min and max per component of each tuples.
1611 * \param [in] epsilon the width of the bbox (identical in each direction) - 0.0 by default
1613 * \return a newly created DataArrayDouble instance having \c this->getNumberOfTuples() tuples and 2 * \c this->getNumberOfComponent() components
1615 * \throw If \a this is not allocated yet.
1617 DataArrayDouble *DataArrayDouble::computeBBoxPerTuple(double epsilon) const
1620 const double *dataPtr=getConstPointer();
1621 int nbOfCompo=getNumberOfComponents();
1622 int nbTuples=getNumberOfTuples();
1623 MCAuto<DataArrayDouble> bbox=DataArrayDouble::New();
1624 bbox->alloc(nbTuples,2*nbOfCompo);
1625 double *bboxPtr=bbox->getPointer();
1626 for(int i=0;i<nbTuples;i++)
1628 for(int j=0;j<nbOfCompo;j++)
1630 bboxPtr[2*nbOfCompo*i+2*j]=dataPtr[nbOfCompo*i+j]-epsilon;
1631 bboxPtr[2*nbOfCompo*i+2*j+1]=dataPtr[nbOfCompo*i+j]+epsilon;
1638 * For each tuples **t** in \a other, this method retrieves tuples in \a this that are equal to **t**.
1639 * Two tuples are considered equal if the euclidian distance between the two tuples is lower than \a eps.
1641 * \param [in] other a DataArrayDouble having same number of components than \a this.
1642 * \param [in] eps absolute precision representing distance (using infinite norm) between 2 tuples behind which 2 tuples are considered equal.
1643 * \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.
1644 * \a cI allows to extract information in \a c.
1645 * \param [out] cI is an indirection array that allows to extract the data contained in \a c.
1647 * \throw In case of:
1648 * - \a this is not allocated
1649 * - \a other is not allocated or null
1650 * - \a this and \a other do not have the same number of components
1651 * - if number of components of \a this is not in [1,2,3]
1653 * \sa MEDCouplingPointSet::getNodeIdsNearPoints, DataArrayDouble::getDifferentValues
1655 void DataArrayDouble::computeTupleIdsNearTuples(const DataArrayDouble *other, double eps, DataArrayInt *& c, DataArrayInt *& cI) const
1658 throw INTERP_KERNEL::Exception("DataArrayDouble::computeTupleIdsNearTuples : input pointer other is null !");
1660 other->checkAllocated();
1661 int nbOfCompo=getNumberOfComponents();
1662 int otherNbOfCompo=other->getNumberOfComponents();
1663 if(nbOfCompo!=otherNbOfCompo)
1664 throw INTERP_KERNEL::Exception("DataArrayDouble::computeTupleIdsNearTuples : number of components should be equal between this and other !");
1665 int nbOfTuplesOther=other->getNumberOfTuples();
1666 MCAuto<DataArrayInt> cArr(DataArrayInt::New()),cIArr(DataArrayInt::New()); cArr->alloc(0,1); cIArr->pushBackSilent(0);
1671 BBTreePts<3,int> myTree(begin(),0,0,getNumberOfTuples(),eps);
1672 FindTupleIdsNearTuplesAlg<3>(myTree,other->getConstPointer(),nbOfTuplesOther,eps,cArr,cIArr);
1677 BBTreePts<2,int> myTree(begin(),0,0,getNumberOfTuples(),eps);
1678 FindTupleIdsNearTuplesAlg<2>(myTree,other->getConstPointer(),nbOfTuplesOther,eps,cArr,cIArr);
1683 BBTreePts<1,int> myTree(begin(),0,0,getNumberOfTuples(),eps);
1684 FindTupleIdsNearTuplesAlg<1>(myTree,other->getConstPointer(),nbOfTuplesOther,eps,cArr,cIArr);
1688 throw INTERP_KERNEL::Exception("Unexpected spacedim of coords for computeTupleIdsNearTuples. Must be 1, 2 or 3.");
1690 c=cArr.retn(); cI=cIArr.retn();
1694 * 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
1695 * around origin of 'radius' 1.
1697 * \param [in] eps absolute epsilon. under that value of delta between max and min no scale is performed.
1699 void DataArrayDouble::recenterForMaxPrecision(double eps)
1702 int dim=getNumberOfComponents();
1703 std::vector<double> bounds(2*dim);
1704 getMinMaxPerComponent(&bounds[0]);
1705 for(int i=0;i<dim;i++)
1707 double delta=bounds[2*i+1]-bounds[2*i];
1708 double offset=(bounds[2*i]+bounds[2*i+1])/2.;
1710 applyLin(1./delta,-offset/delta,i);
1712 applyLin(1.,-offset,i);
1717 * Returns the maximal value and all its locations within \a this one-dimensional array.
1718 * \param [out] tupleIds - a new instance of DataArrayInt containg indices of
1719 * tuples holding the maximal value. The caller is to delete it using
1720 * decrRef() as it is no more needed.
1721 * \return double - the maximal value among all values of \a this array.
1722 * \throw If \a this->getNumberOfComponents() != 1
1723 * \throw If \a this->getNumberOfTuples() < 1
1725 double DataArrayDouble::getMaxValue2(DataArrayInt*& tupleIds) const
1729 double ret=getMaxValue(tmp);
1730 tupleIds=findIdsInRange(ret,ret);
1735 * Returns the minimal value and all its locations within \a this one-dimensional array.
1736 * \param [out] tupleIds - a new instance of DataArrayInt containg indices of
1737 * tuples holding the minimal value. The caller is to delete it using
1738 * decrRef() as it is no more needed.
1739 * \return double - the minimal value among all values of \a this array.
1740 * \throw If \a this->getNumberOfComponents() != 1
1741 * \throw If \a this->getNumberOfTuples() < 1
1743 double DataArrayDouble::getMinValue2(DataArrayInt*& tupleIds) const
1747 double ret=getMinValue(tmp);
1748 tupleIds=findIdsInRange(ret,ret);
1753 * 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.
1754 * This method only works for single component array.
1756 * \return a value in [ 0, \c this->getNumberOfTuples() )
1758 * \throw If \a this is not allocated
1761 int DataArrayDouble::count(double value, double eps) const
1765 if(getNumberOfComponents()!=1)
1766 throw INTERP_KERNEL::Exception("DataArrayDouble::count : must be applied on DataArrayDouble with only one component, you can call 'rearrange' method before !");
1767 const double *vals=begin();
1768 int nbOfTuples=getNumberOfTuples();
1769 for(int i=0;i<nbOfTuples;i++,vals++)
1770 if(fabs(*vals-value)<=eps)
1776 * Returns the average value of \a this one-dimensional array.
1777 * \return double - the average value over all values of \a this array.
1778 * \throw If \a this->getNumberOfComponents() != 1
1779 * \throw If \a this->getNumberOfTuples() < 1
1781 double DataArrayDouble::getAverageValue() const
1783 if(getNumberOfComponents()!=1)
1784 throw INTERP_KERNEL::Exception("DataArrayDouble::getAverageValue : must be applied on DataArrayDouble with only one component, you can call 'rearrange' method before !");
1785 int nbOfTuples=getNumberOfTuples();
1787 throw INTERP_KERNEL::Exception("DataArrayDouble::getAverageValue : array exists but number of tuples must be > 0 !");
1788 const double *vals=getConstPointer();
1789 double ret=std::accumulate(vals,vals+nbOfTuples,0.);
1790 return ret/nbOfTuples;
1794 * Returns the Euclidean norm of the vector defined by \a this array.
1795 * \return double - the value of the Euclidean norm, i.e.
1796 * the square root of the inner product of vector.
1797 * \throw If \a this is not allocated.
1799 double DataArrayDouble::norm2() const
1803 std::size_t nbOfElems=getNbOfElems();
1804 const double *pt=getConstPointer();
1805 for(std::size_t i=0;i<nbOfElems;i++,pt++)
1811 * Returns the maximum norm of the vector defined by \a this array.
1812 * This method works even if the number of components is diferent from one.
1813 * If the number of elements in \a this is 0, -1. is returned.
1814 * \return double - the value of the maximum norm, i.e.
1815 * the maximal absolute value among values of \a this array (whatever its number of components).
1816 * \throw If \a this is not allocated.
1818 double DataArrayDouble::normMax() const
1822 std::size_t nbOfElems(getNbOfElems());
1823 const double *pt(getConstPointer());
1824 for(std::size_t i=0;i<nbOfElems;i++,pt++)
1826 double val(std::abs(*pt));
1834 * Returns the minimum norm (absolute value) of the vector defined by \a this array.
1835 * This method works even if the number of components is diferent from one.
1836 * If the number of elements in \a this is 0, std::numeric_limits<double>::max() is returned.
1837 * \return double - the value of the minimum norm, i.e.
1838 * the minimal absolute value among values of \a this array (whatever its number of components).
1839 * \throw If \a this is not allocated.
1841 double DataArrayDouble::normMin() const
1844 double ret(std::numeric_limits<double>::max());
1845 std::size_t nbOfElems(getNbOfElems());
1846 const double *pt(getConstPointer());
1847 for(std::size_t i=0;i<nbOfElems;i++,pt++)
1849 double val(std::abs(*pt));
1857 * Accumulates values of each component of \a this array.
1858 * \param [out] res - an array of length \a this->getNumberOfComponents(), allocated
1859 * by the caller, that is filled by this method with sum value for each
1861 * \throw If \a this is not allocated.
1863 void DataArrayDouble::accumulate(double *res) const
1866 const double *ptr=getConstPointer();
1867 int nbTuple=getNumberOfTuples();
1868 int nbComps=getNumberOfComponents();
1869 std::fill(res,res+nbComps,0.);
1870 for(int i=0;i<nbTuple;i++)
1871 std::transform(ptr+i*nbComps,ptr+(i+1)*nbComps,res,res,std::plus<double>());
1875 * This method returns the min distance from an external tuple defined by [ \a tupleBg , \a tupleEnd ) to \a this and
1876 * the first tuple in \a this that matches the returned distance. If there is no tuples in \a this an exception will be thrown.
1879 * \a this is expected to be allocated and expected to have a number of components equal to the distance from \a tupleBg to
1880 * \a tupleEnd. If not an exception will be thrown.
1882 * \param [in] tupleBg start pointer (included) of input external tuple
1883 * \param [in] tupleEnd end pointer (not included) of input external tuple
1884 * \param [out] tupleId the tuple id in \a this that matches the min of distance between \a this and input external tuple
1885 * \return the min distance.
1886 * \sa MEDCouplingUMesh::distanceToPoint
1888 double DataArrayDouble::distanceToTuple(const double *tupleBg, const double *tupleEnd, int& tupleId) const
1891 int nbTuple=getNumberOfTuples();
1892 int nbComps=getNumberOfComponents();
1893 if(nbComps!=(int)std::distance(tupleBg,tupleEnd))
1894 { 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()); }
1896 throw INTERP_KERNEL::Exception("DataArrayDouble::distanceToTuple : no tuple in this ! No distance to compute !");
1897 double ret0=std::numeric_limits<double>::max();
1899 const double *work=getConstPointer();
1900 for(int i=0;i<nbTuple;i++)
1903 for(int j=0;j<nbComps;j++,work++)
1904 val+=(*work-tupleBg[j])*((*work-tupleBg[j]));
1908 { ret0=val; tupleId=i; }
1914 * Accumulate values of the given component of \a this array.
1915 * \param [in] compId - the index of the component of interest.
1916 * \return double - a sum value of \a compId-th component.
1917 * \throw If \a this is not allocated.
1918 * \throw If \a the condition ( 0 <= \a compId < \a this->getNumberOfComponents() ) is
1921 double DataArrayDouble::accumulate(int compId) const
1924 const double *ptr=getConstPointer();
1925 int nbTuple=getNumberOfTuples();
1926 int nbComps=getNumberOfComponents();
1927 if(compId<0 || compId>=nbComps)
1928 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulate : Invalid compId specified : No such nb of components !");
1930 for(int i=0;i<nbTuple;i++)
1931 ret+=ptr[i*nbComps+compId];
1936 * This method accumulate using addition tuples in \a this using input index array [ \a bgOfIndex, \a endOfIndex ).
1937 * The returned array will have same number of components than \a this and number of tuples equal to
1938 * \c std::distance(bgOfIndex,endOfIndex) \b minus \b one.
1940 * The input index array is expected to be ascendingly sorted in which the all referenced ids should be in [0, \c this->getNumberOfTuples).
1941 * 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.
1943 * \param [in] bgOfIndex - begin (included) of the input index array.
1944 * \param [in] endOfIndex - end (excluded) of the input index array.
1945 * \return DataArrayDouble * - the new instance having the same number of components than \a this.
1947 * \throw If bgOfIndex or end is NULL.
1948 * \throw If input index array is not ascendingly sorted.
1949 * \throw If there is an id in [ \a bgOfIndex, \a endOfIndex ) not in [0, \c this->getNumberOfTuples).
1950 * \throw If std::distance(bgOfIndex,endOfIndex)==0.
1952 DataArrayDouble *DataArrayDouble::accumulatePerChunck(const int *bgOfIndex, const int *endOfIndex) const
1954 if(!bgOfIndex || !endOfIndex)
1955 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulatePerChunck : input pointer NULL !");
1957 int nbCompo=getNumberOfComponents();
1958 int nbOfTuples=getNumberOfTuples();
1959 int sz=(int)std::distance(bgOfIndex,endOfIndex);
1961 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulatePerChunck : invalid size of input index array !");
1963 MCAuto<DataArrayDouble> ret=DataArrayDouble::New(); ret->alloc(sz,nbCompo);
1964 const int *w=bgOfIndex;
1965 if(*w<0 || *w>=nbOfTuples)
1966 throw INTERP_KERNEL::Exception("DataArrayDouble::accumulatePerChunck : The first element of the input index not in [0,nbOfTuples) !");
1967 const double *srcPt=begin()+(*w)*nbCompo;
1968 double *tmp=ret->getPointer();
1969 for(int i=0;i<sz;i++,tmp+=nbCompo,w++)
1971 std::fill(tmp,tmp+nbCompo,0.);
1974 for(int j=w[0];j<w[1];j++,srcPt+=nbCompo)
1976 if(j>=0 && j<nbOfTuples)
1977 std::transform(srcPt,srcPt+nbCompo,tmp,tmp,std::plus<double>());
1980 std::ostringstream oss; oss << "DataArrayDouble::accumulatePerChunck : At rank #" << i << " the input index array points to id " << j << " should be in [0," << nbOfTuples << ") !";
1981 throw INTERP_KERNEL::Exception(oss.str().c_str());
1987 std::ostringstream oss; oss << "DataArrayDouble::accumulatePerChunck : At rank #" << i << " the input index array is not in ascendingly sorted.";
1988 throw INTERP_KERNEL::Exception(oss.str().c_str());
1991 ret->copyStringInfoFrom(*this);
1996 * 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.
1997 * This method expects that \a this as only one component. The returned array will have \a this->getNumberOfTuples()+1 tuple with also one component.
1998 * The ith element of returned array is equal to the sum of elements in \a this with rank strictly lower than i.
2000 * \return DataArrayDouble - A newly built array containing cum sum of \a this.
2002 MCAuto<DataArrayDouble> DataArrayDouble::cumSum() const
2005 checkNbOfComps(1,"DataArrayDouble::cumSum : this is expected to be single component");
2006 int nbOfTuple(getNumberOfTuples());
2007 MCAuto<DataArrayDouble> ret(DataArrayDouble::New()); ret->alloc(nbOfTuple+1,1);
2008 double *ptr(ret->getPointer());
2010 const double *thisPtr(begin());
2011 for(int i=0;i<nbOfTuple;i++)
2012 ptr[i+1]=ptr[i]+thisPtr[i];
2017 * Converts each 2D point defined by the tuple of \a this array from the Polar to the
2018 * Cartesian coordinate system. The two components of the tuple of \a this array are
2019 * considered to contain (1) radius and (2) angle of the point in the Polar CS.
2020 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
2021 * contains X and Y coordinates of the point in the Cartesian CS. The caller
2022 * is to delete this array using decrRef() as it is no more needed. The array
2023 * does not contain any textual info on components.
2024 * \throw If \a this->getNumberOfComponents() != 2.
2025 * \sa fromCartToPolar
2027 DataArrayDouble *DataArrayDouble::fromPolarToCart() const
2030 int nbOfComp(getNumberOfComponents());
2032 throw INTERP_KERNEL::Exception("DataArrayDouble::fromPolarToCart : must be an array with exactly 2 components !");
2033 int nbOfTuple(getNumberOfTuples());
2034 DataArrayDouble *ret(DataArrayDouble::New());
2035 ret->alloc(nbOfTuple,2);
2036 double *w(ret->getPointer());
2037 const double *wIn(getConstPointer());
2038 for(int i=0;i<nbOfTuple;i++,w+=2,wIn+=2)
2040 w[0]=wIn[0]*cos(wIn[1]);
2041 w[1]=wIn[0]*sin(wIn[1]);
2047 * Converts each 3D point defined by the tuple of \a this array from the Cylindrical to
2048 * the Cartesian coordinate system. The three components of the tuple of \a this array
2049 * are considered to contain (1) radius, (2) azimuth and (3) altitude of the point in
2050 * the Cylindrical CS.
2051 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
2052 * contains X, Y and Z coordinates of the point in the Cartesian CS. The info
2053 * on the third component is copied from \a this array. The caller
2054 * is to delete this array using decrRef() as it is no more needed.
2055 * \throw If \a this->getNumberOfComponents() != 3.
2058 DataArrayDouble *DataArrayDouble::fromCylToCart() const
2061 int nbOfComp(getNumberOfComponents());
2063 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCylToCart : must be an array with exactly 3 components !");
2064 int nbOfTuple(getNumberOfTuples());
2065 DataArrayDouble *ret(DataArrayDouble::New());
2066 ret->alloc(getNumberOfTuples(),3);
2067 double *w(ret->getPointer());
2068 const double *wIn(getConstPointer());
2069 for(int i=0;i<nbOfTuple;i++,w+=3,wIn+=3)
2071 w[0]=wIn[0]*cos(wIn[1]);
2072 w[1]=wIn[0]*sin(wIn[1]);
2075 ret->setInfoOnComponent(2,getInfoOnComponent(2));
2080 * Converts each 3D point defined by the tuple of \a this array from the Spherical to
2081 * the Cartesian coordinate system. The three components of the tuple of \a this array
2082 * are considered to contain (1) radius, (2) polar angle and (3) azimuthal angle of the
2083 * point in the Cylindrical CS.
2084 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
2085 * contains X, Y and Z coordinates of the point in the Cartesian CS. The info
2086 * on the third component is copied from \a this array. The caller
2087 * is to delete this array using decrRef() as it is no more needed.
2088 * \throw If \a this->getNumberOfComponents() != 3.
2089 * \sa fromCartToSpher
2091 DataArrayDouble *DataArrayDouble::fromSpherToCart() const
2094 int nbOfComp(getNumberOfComponents());
2096 throw INTERP_KERNEL::Exception("DataArrayDouble::fromSpherToCart : must be an array with exactly 3 components !");
2097 int nbOfTuple(getNumberOfTuples());
2098 DataArrayDouble *ret(DataArrayDouble::New());
2099 ret->alloc(getNumberOfTuples(),3);
2100 double *w(ret->getPointer());
2101 const double *wIn(getConstPointer());
2102 for(int i=0;i<nbOfTuple;i++,w+=3,wIn+=3)
2104 w[0]=wIn[0]*cos(wIn[2])*sin(wIn[1]);
2105 w[1]=wIn[0]*sin(wIn[2])*sin(wIn[1]);
2106 w[2]=wIn[0]*cos(wIn[1]);
2112 * 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.
2113 * 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.
2114 * If \a at equals to AX_CYL the returned array will be the result of operation cylindric to cartesian of \a this...
2116 * \param [in] atOfThis - The axis type of \a this.
2117 * \return DataArrayDouble * - the new instance of DataArrayDouble (that must be dealed by caller) containing the result of the cartesianizification of \a this.
2119 DataArrayDouble *DataArrayDouble::cartesianize(MEDCouplingAxisType atOfThis) const
2122 int nbOfComp(getNumberOfComponents());
2123 MCAuto<DataArrayDouble> ret;
2131 ret=fromCylToCart();
2136 ret=fromPolarToCart();
2140 throw INTERP_KERNEL::Exception("DataArrayDouble::cartesianize : For AX_CYL, number of components must be in [2,3] !");
2144 ret=fromSpherToCart();
2149 ret=fromPolarToCart();
2153 throw INTERP_KERNEL::Exception("DataArrayDouble::cartesianize : For AX_CYL, number of components must be in [2,3] !");
2155 throw INTERP_KERNEL::Exception("DataArrayDouble::cartesianize : not recognized axis type ! Only AX_CART, AX_CYL and AX_SPHER supported !");
2157 ret->copyStringInfoFrom(*this);
2162 * This method returns a newly created array to be deallocated that contains the result of conversion from cartesian to polar.
2163 * This method expects that \a this has exactly 2 components.
2164 * \sa fromPolarToCart
2166 DataArrayDouble *DataArrayDouble::fromCartToPolar() const
2168 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2170 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2172 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToPolar : must be an array with exactly 2 components !");
2173 ret->alloc(nbTuples,2);
2174 double *retPtr(ret->getPointer());
2175 const double *ptr(begin());
2176 for(int i=0;i<nbTuples;i++,ptr+=2,retPtr+=2)
2178 retPtr[0]=sqrt(ptr[0]*ptr[0]+ptr[1]*ptr[1]);
2179 retPtr[1]=atan2(ptr[1],ptr[0]);
2185 * This method returns a newly created array to be deallocated that contains the result of conversion from cartesian to cylindrical.
2186 * This method expects that \a this has exactly 3 components.
2189 DataArrayDouble *DataArrayDouble::fromCartToCyl() const
2191 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2193 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2195 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCyl : must be an array with exactly 3 components !");
2196 ret->alloc(nbTuples,3);
2197 double *retPtr(ret->getPointer());
2198 const double *ptr(begin());
2199 for(int i=0;i<nbTuples;i++,ptr+=3,retPtr+=3)
2201 retPtr[0]=sqrt(ptr[0]*ptr[0]+ptr[1]*ptr[1]);
2202 retPtr[1]=atan2(ptr[1],ptr[0]);
2209 * This method returns a newly created array to be deallocated that contains the result of conversion from cartesian to spherical coordinates.
2210 * \sa fromSpherToCart
2212 DataArrayDouble *DataArrayDouble::fromCartToSpher() const
2214 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2216 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2218 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToSpher : must be an array with exactly 3 components !");
2219 ret->alloc(nbTuples,3);
2220 double *retPtr(ret->getPointer());
2221 const double *ptr(begin());
2222 for(int i=0;i<nbTuples;i++,ptr+=3,retPtr+=3)
2224 retPtr[0]=sqrt(ptr[0]*ptr[0]+ptr[1]*ptr[1]+ptr[2]*ptr[2]);
2225 retPtr[1]=acos(ptr[2]/retPtr[0]);
2226 retPtr[2]=atan2(ptr[1],ptr[0]);
2232 * 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.
2233 * This method expects that \a this has exactly 3 components.
2234 * \sa MEDCouplingFieldDouble::computeVectorFieldCyl
2236 DataArrayDouble *DataArrayDouble::fromCartToCylGiven(const DataArrayDouble *coords, const double center[3], const double vect[3]) const
2239 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : input coords are NULL !");
2240 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2241 checkAllocated(); coords->checkAllocated();
2242 int nbOfComp(getNumberOfComponents()),nbTuples(getNumberOfTuples());
2244 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : must be an array with exactly 3 components !");
2245 if(coords->getNumberOfComponents()!=3)
2246 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : coords array must have exactly 3 components !");
2247 if(coords->getNumberOfTuples()!=nbTuples)
2248 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : coords array must have the same number of tuples !");
2249 ret->alloc(nbTuples,nbOfComp);
2250 double magOfVect(sqrt(vect[0]*vect[0]+vect[1]*vect[1]+vect[2]*vect[2]));
2252 throw INTERP_KERNEL::Exception("DataArrayDouble::fromCartToCylGiven : magnitude of vect is too low !");
2253 double Ur[3],Uteta[3],Uz[3],*retPtr(ret->getPointer());
2254 const double *coo(coords->begin()),*vectField(begin());
2255 std::transform(vect,vect+3,Uz,std::bind2nd(std::multiplies<double>(),1./magOfVect));
2256 for(int i=0;i<nbTuples;i++,vectField+=3,retPtr+=3,coo+=3)
2258 std::transform(coo,coo+3,center,Ur,std::minus<double>());
2259 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];
2260 double magOfTeta(sqrt(Uteta[0]*Uteta[0]+Uteta[1]*Uteta[1]+Uteta[2]*Uteta[2]));
2261 std::transform(Uteta,Uteta+3,Uteta,std::bind2nd(std::multiplies<double>(),1./magOfTeta));
2262 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];
2263 retPtr[0]=Ur[0]*vectField[0]+Ur[1]*vectField[1]+Ur[2]*vectField[2];
2264 retPtr[1]=Uteta[0]*vectField[0]+Uteta[1]*vectField[1]+Uteta[2]*vectField[2];
2265 retPtr[2]=Uz[0]*vectField[0]+Uz[1]*vectField[1]+Uz[2]*vectField[2];
2267 ret->copyStringInfoFrom(*this);
2272 * Computes the doubly contracted product of every tensor defined by the tuple of \a this
2273 * array contating 6 components.
2274 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
2275 * is calculated from the tuple <em>(t)</em> of \a this array as follows:
2276 * \f$ t[0]^2+t[1]^2+t[2]^2+2*t[3]^2+2*t[4]^2+2*t[5]^2\f$.
2277 * The caller is to delete this result array using decrRef() as it is no more needed.
2278 * \throw If \a this->getNumberOfComponents() != 6.
2280 DataArrayDouble *DataArrayDouble::doublyContractedProduct() const
2283 int nbOfComp(getNumberOfComponents());
2285 throw INTERP_KERNEL::Exception("DataArrayDouble::doublyContractedProduct : must be an array with exactly 6 components !");
2286 DataArrayDouble *ret=DataArrayDouble::New();
2287 int nbOfTuple=getNumberOfTuples();
2288 ret->alloc(nbOfTuple,1);
2289 const double *src=getConstPointer();
2290 double *dest=ret->getPointer();
2291 for(int i=0;i<nbOfTuple;i++,dest++,src+=6)
2292 *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];
2297 * Computes the determinant of every square matrix defined by the tuple of \a this
2298 * array, which contains either 4, 6 or 9 components. The case of 6 components
2299 * corresponds to that of the upper triangular matrix.
2300 * \return DataArrayDouble * - the new instance of DataArrayDouble, whose each tuple
2301 * is the determinant of matrix of the corresponding tuple of \a this array.
2302 * The caller is to delete this result array using decrRef() as it is no more
2304 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2306 DataArrayDouble *DataArrayDouble::determinant() const
2309 DataArrayDouble *ret=DataArrayDouble::New();
2310 int nbOfTuple=getNumberOfTuples();
2311 ret->alloc(nbOfTuple,1);
2312 const double *src=getConstPointer();
2313 double *dest=ret->getPointer();
2314 switch(getNumberOfComponents())
2317 for(int i=0;i<nbOfTuple;i++,dest++,src+=6)
2318 *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];
2321 for(int i=0;i<nbOfTuple;i++,dest++,src+=4)
2322 *dest=src[0]*src[3]-src[1]*src[2];
2325 for(int i=0;i<nbOfTuple;i++,dest++,src+=9)
2326 *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];
2330 throw INTERP_KERNEL::Exception("DataArrayDouble::determinant : Invalid number of components ! must be in 4,6,9 !");
2335 * Computes 3 eigenvalues of every upper triangular matrix defined by the tuple of
2336 * \a this array, which contains 6 components.
2337 * \return DataArrayDouble * - the new instance of DataArrayDouble containing 3
2338 * components, whose each tuple contains the eigenvalues of the matrix of
2339 * corresponding tuple of \a this array.
2340 * The caller is to delete this result array using decrRef() as it is no more
2342 * \throw If \a this->getNumberOfComponents() != 6.
2344 DataArrayDouble *DataArrayDouble::eigenValues() const
2347 int nbOfComp=getNumberOfComponents();
2349 throw INTERP_KERNEL::Exception("DataArrayDouble::eigenValues : must be an array with exactly 6 components !");
2350 DataArrayDouble *ret=DataArrayDouble::New();
2351 int nbOfTuple=getNumberOfTuples();
2352 ret->alloc(nbOfTuple,3);
2353 const double *src=getConstPointer();
2354 double *dest=ret->getPointer();
2355 for(int i=0;i<nbOfTuple;i++,dest+=3,src+=6)
2356 INTERP_KERNEL::computeEigenValues6(src,dest);
2361 * Computes 3 eigenvectors of every upper triangular matrix defined by the tuple of
2362 * \a this array, which contains 6 components.
2363 * \return DataArrayDouble * - the new instance of DataArrayDouble containing 9
2364 * components, whose each tuple contains 3 eigenvectors of the matrix of
2365 * corresponding tuple of \a this array.
2366 * The caller is to delete this result array using decrRef() as it is no more
2368 * \throw If \a this->getNumberOfComponents() != 6.
2370 DataArrayDouble *DataArrayDouble::eigenVectors() const
2373 int nbOfComp=getNumberOfComponents();
2375 throw INTERP_KERNEL::Exception("DataArrayDouble::eigenVectors : must be an array with exactly 6 components !");
2376 DataArrayDouble *ret=DataArrayDouble::New();
2377 int nbOfTuple=getNumberOfTuples();
2378 ret->alloc(nbOfTuple,9);
2379 const double *src=getConstPointer();
2380 double *dest=ret->getPointer();
2381 for(int i=0;i<nbOfTuple;i++,src+=6)
2384 INTERP_KERNEL::computeEigenValues6(src,tmp);
2385 for(int j=0;j<3;j++,dest+=3)
2386 INTERP_KERNEL::computeEigenVectorForEigenValue6(src,tmp[j],1e-12,dest);
2392 * Computes the inverse matrix of every matrix defined by the tuple of \a this
2393 * array, which contains either 4, 6 or 9 components. The case of 6 components
2394 * corresponds to that of the upper triangular matrix.
2395 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2396 * same number of components as \a this one, whose each tuple is the inverse
2397 * matrix of the matrix of corresponding tuple of \a this array.
2398 * The caller is to delete this result array using decrRef() as it is no more
2400 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2402 DataArrayDouble *DataArrayDouble::inverse() const
2405 int nbOfComp=getNumberOfComponents();
2406 if(nbOfComp!=6 && nbOfComp!=9 && nbOfComp!=4)
2407 throw INTERP_KERNEL::Exception("DataArrayDouble::inversion : must be an array with 4,6 or 9 components !");
2408 DataArrayDouble *ret=DataArrayDouble::New();
2409 int nbOfTuple=getNumberOfTuples();
2410 ret->alloc(nbOfTuple,nbOfComp);
2411 const double *src=getConstPointer();
2412 double *dest=ret->getPointer();
2414 for(int i=0;i<nbOfTuple;i++,dest+=6,src+=6)
2416 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];
2417 dest[0]=(src[1]*src[2]-src[4]*src[4])/det;
2418 dest[1]=(src[0]*src[2]-src[5]*src[5])/det;
2419 dest[2]=(src[0]*src[1]-src[3]*src[3])/det;
2420 dest[3]=(src[5]*src[4]-src[3]*src[2])/det;
2421 dest[4]=(src[5]*src[3]-src[0]*src[4])/det;
2422 dest[5]=(src[3]*src[4]-src[1]*src[5])/det;
2424 else if(nbOfComp==4)
2425 for(int i=0;i<nbOfTuple;i++,dest+=4,src+=4)
2427 double det=src[0]*src[3]-src[1]*src[2];
2429 dest[1]=-src[1]/det;
2430 dest[2]=-src[2]/det;
2434 for(int i=0;i<nbOfTuple;i++,dest+=9,src+=9)
2436 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];
2437 dest[0]=(src[4]*src[8]-src[7]*src[5])/det;
2438 dest[1]=(src[7]*src[2]-src[1]*src[8])/det;
2439 dest[2]=(src[1]*src[5]-src[4]*src[2])/det;
2440 dest[3]=(src[6]*src[5]-src[3]*src[8])/det;
2441 dest[4]=(src[0]*src[8]-src[6]*src[2])/det;
2442 dest[5]=(src[2]*src[3]-src[0]*src[5])/det;
2443 dest[6]=(src[3]*src[7]-src[6]*src[4])/det;
2444 dest[7]=(src[6]*src[1]-src[0]*src[7])/det;
2445 dest[8]=(src[0]*src[4]-src[1]*src[3])/det;
2451 * Computes the trace of every matrix defined by the tuple of \a this
2452 * array, which contains either 4, 6 or 9 components. The case of 6 components
2453 * corresponds to that of the upper triangular matrix.
2454 * \return DataArrayDouble * - the new instance of DataArrayDouble containing
2455 * 1 component, whose each tuple is the trace of
2456 * the matrix of corresponding tuple of \a this array.
2457 * The caller is to delete this result array using decrRef() as it is no more
2459 * \throw If \a this->getNumberOfComponents() is not in [4,6,9].
2461 DataArrayDouble *DataArrayDouble::trace() const
2464 int nbOfComp=getNumberOfComponents();
2465 if(nbOfComp!=6 && nbOfComp!=9 && nbOfComp!=4)
2466 throw INTERP_KERNEL::Exception("DataArrayDouble::trace : must be an array with 4,6 or 9 components !");
2467 DataArrayDouble *ret=DataArrayDouble::New();
2468 int nbOfTuple=getNumberOfTuples();
2469 ret->alloc(nbOfTuple,1);
2470 const double *src=getConstPointer();
2471 double *dest=ret->getPointer();
2473 for(int i=0;i<nbOfTuple;i++,dest++,src+=6)
2474 *dest=src[0]+src[1]+src[2];
2475 else if(nbOfComp==4)
2476 for(int i=0;i<nbOfTuple;i++,dest++,src+=4)
2477 *dest=src[0]+src[3];
2479 for(int i=0;i<nbOfTuple;i++,dest++,src+=9)
2480 *dest=src[0]+src[4]+src[8];
2485 * Computes the stress deviator tensor of every stress tensor defined by the tuple of
2486 * \a this array, which contains 6 components.
2487 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2488 * same number of components and tuples as \a this array.
2489 * The caller is to delete this result array using decrRef() as it is no more
2491 * \throw If \a this->getNumberOfComponents() != 6.
2493 DataArrayDouble *DataArrayDouble::deviator() const
2496 int nbOfComp=getNumberOfComponents();
2498 throw INTERP_KERNEL::Exception("DataArrayDouble::deviator : must be an array with exactly 6 components !");
2499 DataArrayDouble *ret=DataArrayDouble::New();
2500 int nbOfTuple=getNumberOfTuples();
2501 ret->alloc(nbOfTuple,6);
2502 const double *src=getConstPointer();
2503 double *dest=ret->getPointer();
2504 for(int i=0;i<nbOfTuple;i++,dest+=6,src+=6)
2506 double tr=(src[0]+src[1]+src[2])/3.;
2518 * Computes the magnitude of every vector defined by the tuple of
2520 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2521 * same number of tuples as \a this array and one component.
2522 * The caller is to delete this result array using decrRef() as it is no more
2524 * \throw If \a this is not allocated.
2526 DataArrayDouble *DataArrayDouble::magnitude() const
2529 int nbOfComp=getNumberOfComponents();
2530 DataArrayDouble *ret=DataArrayDouble::New();
2531 int nbOfTuple=getNumberOfTuples();
2532 ret->alloc(nbOfTuple,1);
2533 const double *src=getConstPointer();
2534 double *dest=ret->getPointer();
2535 for(int i=0;i<nbOfTuple;i++,dest++)
2538 for(int j=0;j<nbOfComp;j++,src++)
2546 * Computes for each tuple the sum of number of components values in the tuple and return it.
2548 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2549 * same number of tuples as \a this array and one component.
2550 * The caller is to delete this result array using decrRef() as it is no more
2552 * \throw If \a this is not allocated.
2554 DataArrayDouble *DataArrayDouble::sumPerTuple() const
2557 int nbOfComp(getNumberOfComponents()),nbOfTuple(getNumberOfTuples());
2558 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
2559 ret->alloc(nbOfTuple,1);
2560 const double *src(getConstPointer());
2561 double *dest(ret->getPointer());
2562 for(int i=0;i<nbOfTuple;i++,dest++,src+=nbOfComp)
2563 *dest=std::accumulate(src,src+nbOfComp,0.);
2568 * Computes the maximal value within every tuple of \a this array.
2569 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2570 * same number of tuples as \a this array and one component.
2571 * The caller is to delete this result array using decrRef() as it is no more
2573 * \throw If \a this is not allocated.
2574 * \sa DataArrayDouble::maxPerTupleWithCompoId
2576 DataArrayDouble *DataArrayDouble::maxPerTuple() const
2579 int nbOfComp=getNumberOfComponents();
2580 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
2581 int nbOfTuple=getNumberOfTuples();
2582 ret->alloc(nbOfTuple,1);
2583 const double *src=getConstPointer();
2584 double *dest=ret->getPointer();
2585 for(int i=0;i<nbOfTuple;i++,dest++,src+=nbOfComp)
2586 *dest=*std::max_element(src,src+nbOfComp);
2591 * Computes the maximal value within every tuple of \a this array and it returns the first component
2592 * id for each tuple that corresponds to the maximal value within the tuple.
2594 * \param [out] compoIdOfMaxPerTuple - the new new instance of DataArrayInt containing the
2595 * same number of tuples and only one component.
2596 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2597 * same number of tuples as \a this array and one component.
2598 * The caller is to delete this result array using decrRef() as it is no more
2600 * \throw If \a this is not allocated.
2601 * \sa DataArrayDouble::maxPerTuple
2603 DataArrayDouble *DataArrayDouble::maxPerTupleWithCompoId(DataArrayInt* &compoIdOfMaxPerTuple) const
2606 int nbOfComp=getNumberOfComponents();
2607 MCAuto<DataArrayDouble> ret0=DataArrayDouble::New();
2608 MCAuto<DataArrayInt> ret1=DataArrayInt::New();
2609 int nbOfTuple=getNumberOfTuples();
2610 ret0->alloc(nbOfTuple,1); ret1->alloc(nbOfTuple,1);
2611 const double *src=getConstPointer();
2612 double *dest=ret0->getPointer(); int *dest1=ret1->getPointer();
2613 for(int i=0;i<nbOfTuple;i++,dest++,dest1++,src+=nbOfComp)
2615 const double *loc=std::max_element(src,src+nbOfComp);
2617 *dest1=(int)std::distance(src,loc);
2619 compoIdOfMaxPerTuple=ret1.retn();
2624 * This method returns a newly allocated DataArrayDouble instance having one component and \c this->getNumberOfTuples() * \c this->getNumberOfTuples() tuples.
2625 * \n This returned array contains the euclidian distance for each tuple in \a this.
2626 * \n So the returned array can be seen as a dense symmetrical matrix whose diagonal elements are equal to 0.
2627 * \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)
2629 * \warning use this method with care because it can leads to big amount of consumed memory !
2631 * \return A newly allocated (huge) MEDCoupling::DataArrayDouble instance that the caller should deal with.
2633 * \throw If \a this is not allocated.
2635 * \sa DataArrayDouble::buildEuclidianDistanceDenseMatrixWith
2637 DataArrayDouble *DataArrayDouble::buildEuclidianDistanceDenseMatrix() const
2640 int nbOfComp=getNumberOfComponents();
2641 int nbOfTuples=getNumberOfTuples();
2642 const double *inData=getConstPointer();
2643 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
2644 ret->alloc(nbOfTuples*nbOfTuples,1);
2645 double *outData=ret->getPointer();
2646 for(int i=0;i<nbOfTuples;i++)
2648 outData[i*nbOfTuples+i]=0.;
2649 for(int j=i+1;j<nbOfTuples;j++)
2652 for(int k=0;k<nbOfComp;k++)
2653 { double delta=inData[i*nbOfComp+k]-inData[j*nbOfComp+k]; dist+=delta*delta; }
2655 outData[i*nbOfTuples+j]=dist;
2656 outData[j*nbOfTuples+i]=dist;
2663 * This method returns a newly allocated DataArrayDouble instance having one component and \c this->getNumberOfTuples() * \c other->getNumberOfTuples() tuples.
2664 * \n This returned array contains the euclidian distance for each tuple in \a other with each tuple in \a this.
2665 * \n So the returned array can be seen as a dense rectangular matrix with \c other->getNumberOfTuples() rows and \c this->getNumberOfTuples() columns.
2666 * \n Output rectangular matrix is sorted along rows.
2667 * \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)
2669 * \warning use this method with care because it can leads to big amount of consumed memory !
2671 * \param [in] other DataArrayDouble instance having same number of components than \a this.
2672 * \return A newly allocated (huge) MEDCoupling::DataArrayDouble instance that the caller should deal with.
2674 * \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.
2676 * \sa DataArrayDouble::buildEuclidianDistanceDenseMatrix
2678 DataArrayDouble *DataArrayDouble::buildEuclidianDistanceDenseMatrixWith(const DataArrayDouble *other) const
2681 throw INTERP_KERNEL::Exception("DataArrayDouble::buildEuclidianDistanceDenseMatrixWith : input parameter is null !");
2683 other->checkAllocated();
2684 int nbOfComp=getNumberOfComponents();
2685 int otherNbOfComp=other->getNumberOfComponents();
2686 if(nbOfComp!=otherNbOfComp)
2688 std::ostringstream oss; oss << "DataArrayDouble::buildEuclidianDistanceDenseMatrixWith : this nb of compo=" << nbOfComp << " and other nb of compo=" << otherNbOfComp << ". It should match !";
2689 throw INTERP_KERNEL::Exception(oss.str().c_str());
2691 int nbOfTuples=getNumberOfTuples();
2692 int otherNbOfTuples=other->getNumberOfTuples();
2693 const double *inData=getConstPointer();
2694 const double *inDataOther=other->getConstPointer();
2695 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
2696 ret->alloc(otherNbOfTuples*nbOfTuples,1);
2697 double *outData=ret->getPointer();
2698 for(int i=0;i<otherNbOfTuples;i++,inDataOther+=nbOfComp)
2700 for(int j=0;j<nbOfTuples;j++)
2703 for(int k=0;k<nbOfComp;k++)
2704 { double delta=inDataOther[k]-inData[j*nbOfComp+k]; dist+=delta*delta; }
2706 outData[i*nbOfTuples+j]=dist;
2713 * Sorts value within every tuple of \a this array.
2714 * \param [in] asc - if \a true, the values are sorted in ascending order, else,
2715 * in descending order.
2716 * \throw If \a this is not allocated.
2718 void DataArrayDouble::sortPerTuple(bool asc)
2721 double *pt=getPointer();
2722 int nbOfTuple=getNumberOfTuples();
2723 int nbOfComp=getNumberOfComponents();
2725 for(int i=0;i<nbOfTuple;i++,pt+=nbOfComp)
2726 std::sort(pt,pt+nbOfComp);
2728 for(int i=0;i<nbOfTuple;i++,pt+=nbOfComp)
2729 std::sort(pt,pt+nbOfComp,std::greater<double>());
2734 * Converts every value of \a this array to its absolute value.
2735 * \b WARNING this method is non const. If a new DataArrayDouble instance should be built containing the result of abs DataArrayDouble::computeAbs
2736 * should be called instead.
2738 * \throw If \a this is not allocated.
2739 * \sa DataArrayDouble::computeAbs
2741 void DataArrayDouble::abs()
2744 double *ptr(getPointer());
2745 std::size_t nbOfElems(getNbOfElems());
2746 std::transform(ptr,ptr+nbOfElems,ptr,std::ptr_fun<double,double>(fabs));
2751 * This method builds a new instance of \a this object containing the result of std::abs applied of all elements in \a this.
2752 * This method is a const method (that do not change any values in \a this) contrary to DataArrayDouble::abs method.
2754 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2755 * same number of tuples and component as \a this array.
2756 * The caller is to delete this result array using decrRef() as it is no more
2758 * \throw If \a this is not allocated.
2759 * \sa DataArrayDouble::abs
2761 DataArrayDouble *DataArrayDouble::computeAbs() const
2764 DataArrayDouble *newArr(DataArrayDouble::New());
2765 int nbOfTuples(getNumberOfTuples());
2766 int nbOfComp(getNumberOfComponents());
2767 newArr->alloc(nbOfTuples,nbOfComp);
2768 std::transform(begin(),end(),newArr->getPointer(),std::ptr_fun<double,double>(fabs));
2769 newArr->copyStringInfoFrom(*this);
2774 * Apply a linear function to a given component of \a this array, so that
2775 * an array element <em>(x)</em> becomes \f$ a * x + b \f$.
2776 * \param [in] a - the first coefficient of the function.
2777 * \param [in] b - the second coefficient of the function.
2778 * \param [in] compoId - the index of component to modify.
2779 * \throw If \a this is not allocated, or \a compoId is not in [0,\c this->getNumberOfComponents() ).
2781 void DataArrayDouble::applyLin(double a, double b, int compoId)
2784 double *ptr(getPointer()+compoId);
2785 int nbOfComp(getNumberOfComponents()),nbOfTuple(getNumberOfTuples());
2786 if(compoId<0 || compoId>=nbOfComp)
2788 std::ostringstream oss; oss << "DataArrayDouble::applyLin : The compoId requested (" << compoId << ") is not valid ! Must be in [0," << nbOfComp << ") !";
2789 throw INTERP_KERNEL::Exception(oss.str().c_str());
2791 for(int i=0;i<nbOfTuple;i++,ptr+=nbOfComp)
2797 * Apply a linear function to all elements of \a this array, so that
2798 * an element _x_ becomes \f$ a * x + b \f$.
2799 * \param [in] a - the first coefficient of the function.
2800 * \param [in] b - the second coefficient of the function.
2801 * \throw If \a this is not allocated.
2803 void DataArrayDouble::applyLin(double a, double b)
2806 double *ptr=getPointer();
2807 std::size_t nbOfElems=getNbOfElems();
2808 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2814 * Modify all elements of \a this array, so that
2815 * an element _x_ becomes \f$ numerator / x \f$.
2816 * \warning If an exception is thrown because of presence of 0.0 element in \a this
2817 * array, all elements processed before detection of the zero element remain
2819 * \param [in] numerator - the numerator used to modify array elements.
2820 * \throw If \a this is not allocated.
2821 * \throw If there is an element equal to 0.0 in \a this array.
2823 void DataArrayDouble::applyInv(double numerator)
2826 double *ptr=getPointer();
2827 std::size_t nbOfElems=getNbOfElems();
2828 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2830 if(std::abs(*ptr)>std::numeric_limits<double>::min())
2832 *ptr=numerator/(*ptr);
2836 std::ostringstream oss; oss << "DataArrayDouble::applyInv : presence of null value in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
2838 throw INTERP_KERNEL::Exception(oss.str().c_str());
2845 * Returns a full copy of \a this array except that sign of all elements is reversed.
2846 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2847 * same number of tuples and component as \a this array.
2848 * The caller is to delete this result array using decrRef() as it is no more
2850 * \throw If \a this is not allocated.
2852 DataArrayDouble *DataArrayDouble::negate() const
2855 DataArrayDouble *newArr=DataArrayDouble::New();
2856 int nbOfTuples=getNumberOfTuples();
2857 int nbOfComp=getNumberOfComponents();
2858 newArr->alloc(nbOfTuples,nbOfComp);
2859 const double *cptr=getConstPointer();
2860 std::transform(cptr,cptr+nbOfTuples*nbOfComp,newArr->getPointer(),std::negate<double>());
2861 newArr->copyStringInfoFrom(*this);
2866 * Modify all elements of \a this array, so that
2867 * an element _x_ becomes <em> val ^ x </em>. Contrary to DataArrayInt::applyPow
2868 * all values in \a this have to be >= 0 if val is \b not integer.
2869 * \param [in] val - the value used to apply pow on all array elements.
2870 * \throw If \a this is not allocated.
2871 * \warning If an exception is thrown because of presence of 0 element in \a this
2872 * array and \a val is \b not integer, all elements processed before detection of the zero element remain
2875 void DataArrayDouble::applyPow(double val)
2878 double *ptr=getPointer();
2879 std::size_t nbOfElems=getNbOfElems();
2881 bool isInt=((double)val2)==val;
2884 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2890 std::ostringstream oss; oss << "DataArrayDouble::applyPow (double) : At elem # " << i << " value is " << *ptr << " ! must be >=0. !";
2891 throw INTERP_KERNEL::Exception(oss.str().c_str());
2897 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2898 *ptr=pow(*ptr,val2);
2904 * Modify all elements of \a this array, so that
2905 * an element _x_ becomes \f$ val ^ x \f$.
2906 * \param [in] val - the value used to apply pow on all array elements.
2907 * \throw If \a this is not allocated.
2908 * \throw If \a val < 0.
2909 * \warning If an exception is thrown because of presence of 0 element in \a this
2910 * array, all elements processed before detection of the zero element remain
2913 void DataArrayDouble::applyRPow(double val)
2917 throw INTERP_KERNEL::Exception("DataArrayDouble::applyRPow : the input value has to be >= 0 !");
2918 double *ptr=getPointer();
2919 std::size_t nbOfElems=getNbOfElems();
2920 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
2926 * Returns a new DataArrayDouble created from \a this one by applying \a
2927 * FunctionToEvaluate to every tuple of \a this array. Textual data is not copied.
2928 * For more info see \ref MEDCouplingArrayApplyFunc
2929 * \param [in] nbOfComp - number of components in the result array.
2930 * \param [in] func - the \a FunctionToEvaluate declared as
2931 * \c bool (*\a func)(\c const \c double *\a pos, \c double *\a res),
2932 * where \a pos points to the first component of a tuple of \a this array
2933 * and \a res points to the first component of a tuple of the result array.
2934 * Note that length (number of components) of \a pos can differ from
2936 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2937 * same number of tuples as \a this array.
2938 * The caller is to delete this result array using decrRef() as it is no more
2940 * \throw If \a this is not allocated.
2941 * \throw If \a func returns \a false.
2943 DataArrayDouble *DataArrayDouble::applyFunc(int nbOfComp, FunctionToEvaluate func) const
2946 DataArrayDouble *newArr=DataArrayDouble::New();
2947 int nbOfTuples=getNumberOfTuples();
2948 int oldNbOfComp=getNumberOfComponents();
2949 newArr->alloc(nbOfTuples,nbOfComp);
2950 const double *ptr=getConstPointer();
2951 double *ptrToFill=newArr->getPointer();
2952 for(int i=0;i<nbOfTuples;i++)
2954 if(!func(ptr+i*oldNbOfComp,ptrToFill+i*nbOfComp))
2956 std::ostringstream oss; oss << "For tuple # " << i << " with value (";
2957 std::copy(ptr+oldNbOfComp*i,ptr+oldNbOfComp*(i+1),std::ostream_iterator<double>(oss,", "));
2958 oss << ") : Evaluation of function failed !";
2960 throw INTERP_KERNEL::Exception(oss.str().c_str());
2967 * Returns a new DataArrayDouble created from \a this one by applying a function to every
2968 * tuple of \a this array. Textual data is not copied.
2969 * For more info see \ref MEDCouplingArrayApplyFunc1.
2970 * \param [in] nbOfComp - number of components in the result array.
2971 * \param [in] func - the expression defining how to transform a tuple of \a this array.
2972 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
2973 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
2974 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
2975 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
2976 * same number of tuples as \a this array and \a nbOfComp components.
2977 * The caller is to delete this result array using decrRef() as it is no more
2979 * \throw If \a this is not allocated.
2980 * \throw If computing \a func fails.
2982 DataArrayDouble *DataArrayDouble::applyFunc(int nbOfComp, const std::string& func, bool isSafe) const
2984 INTERP_KERNEL::ExprParser expr(func);
2986 std::set<std::string> vars;
2987 expr.getTrueSetOfVars(vars);
2988 std::vector<std::string> varsV(vars.begin(),vars.end());
2989 return applyFuncNamedCompo(nbOfComp,varsV,func,isSafe);
2993 * Returns a new DataArrayDouble created from \a this one by applying a function to every
2994 * tuple of \a this array. Textual data is not copied. This method works by tuples (whatever its size).
2995 * If \a this is a one component array, call applyFuncOnThis instead that performs the same work faster.
2997 * For more info see \ref MEDCouplingArrayApplyFunc0.
2998 * \param [in] func - the expression defining how to transform a tuple of \a this array.
2999 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
3000 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
3001 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
3002 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
3003 * same number of tuples and components as \a this array.
3004 * The caller is to delete this result array using decrRef() as it is no more
3006 * \sa applyFuncOnThis
3007 * \throw If \a this is not allocated.
3008 * \throw If computing \a func fails.
3010 DataArrayDouble *DataArrayDouble::applyFunc(const std::string& func, bool isSafe) const
3012 int nbOfComp(getNumberOfComponents());
3014 throw INTERP_KERNEL::Exception("DataArrayDouble::applyFunc : output number of component must be > 0 !");
3016 int nbOfTuples(getNumberOfTuples());
3017 MCAuto<DataArrayDouble> newArr(DataArrayDouble::New());
3018 newArr->alloc(nbOfTuples,nbOfComp);
3019 INTERP_KERNEL::ExprParser expr(func);
3021 std::set<std::string> vars;
3022 expr.getTrueSetOfVars(vars);
3023 if((int)vars.size()>1)
3025 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 : ";
3026 std::copy(vars.begin(),vars.end(),std::ostream_iterator<std::string>(oss," "));
3027 throw INTERP_KERNEL::Exception(oss.str().c_str());
3031 expr.prepareFastEvaluator();
3032 newArr->rearrange(1);
3033 newArr->fillWithValue(expr.evaluateDouble());
3034 newArr->rearrange(nbOfComp);
3035 return newArr.retn();
3037 std::vector<std::string> vars2(vars.begin(),vars.end());
3038 double buff,*ptrToFill(newArr->getPointer());
3039 const double *ptr(begin());
3040 std::vector<double> stck;
3041 expr.prepareExprEvaluationDouble(vars2,1,1,0,&buff,&buff+1);
3042 expr.prepareFastEvaluator();
3045 for(int i=0;i<nbOfTuples;i++)
3047 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
3050 expr.evaluateDoubleInternal(stck);
3051 *ptrToFill=stck.back();
3058 for(int i=0;i<nbOfTuples;i++)
3060 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
3065 expr.evaluateDoubleInternalSafe(stck);
3067 catch(INTERP_KERNEL::Exception& e)
3069 std::ostringstream oss; oss << "For tuple # " << i << " component # " << iComp << " with value (";
3071 oss << ") : Evaluation of function failed !" << e.what();
3072 throw INTERP_KERNEL::Exception(oss.str().c_str());
3074 *ptrToFill=stck.back();
3079 return newArr.retn();
3083 * This method is a non const method that modify the array in \a this.
3084 * This method only works on one component array. It means that function \a func must
3085 * contain at most one variable.
3086 * This method is a specialization of applyFunc method with one parameter on one component array.
3088 * \param [in] func - the expression defining how to transform a tuple of \a this array.
3089 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
3090 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
3091 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
3095 void DataArrayDouble::applyFuncOnThis(const std::string& func, bool isSafe)
3097 int nbOfComp(getNumberOfComponents());
3099 throw INTERP_KERNEL::Exception("DataArrayDouble::applyFuncOnThis : output number of component must be > 0 !");
3101 int nbOfTuples(getNumberOfTuples());
3102 INTERP_KERNEL::ExprParser expr(func);
3104 std::set<std::string> vars;
3105 expr.getTrueSetOfVars(vars);
3106 if((int)vars.size()>1)
3108 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 : ";
3109 std::copy(vars.begin(),vars.end(),std::ostream_iterator<std::string>(oss," "));
3110 throw INTERP_KERNEL::Exception(oss.str().c_str());
3114 expr.prepareFastEvaluator();
3115 std::vector<std::string> compInfo(getInfoOnComponents());
3117 fillWithValue(expr.evaluateDouble());
3118 rearrange(nbOfComp);
3119 setInfoOnComponents(compInfo);
3122 std::vector<std::string> vars2(vars.begin(),vars.end());
3123 double buff,*ptrToFill(getPointer());
3124 const double *ptr(begin());
3125 std::vector<double> stck;
3126 expr.prepareExprEvaluationDouble(vars2,1,1,0,&buff,&buff+1);
3127 expr.prepareFastEvaluator();
3130 for(int i=0;i<nbOfTuples;i++)
3132 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
3135 expr.evaluateDoubleInternal(stck);
3136 *ptrToFill=stck.back();
3143 for(int i=0;i<nbOfTuples;i++)
3145 for(int iComp=0;iComp<nbOfComp;iComp++,ptr++,ptrToFill++)
3150 expr.evaluateDoubleInternalSafe(stck);
3152 catch(INTERP_KERNEL::Exception& e)
3154 std::ostringstream oss; oss << "For tuple # " << i << " component # " << iComp << " with value (";
3156 oss << ") : Evaluation of function failed !" << e.what();
3157 throw INTERP_KERNEL::Exception(oss.str().c_str());
3159 *ptrToFill=stck.back();
3167 * Returns a new DataArrayDouble created from \a this one by applying a function to every
3168 * tuple of \a this array. Textual data is not copied.
3169 * For more info see \ref MEDCouplingArrayApplyFunc2.
3170 * \param [in] nbOfComp - number of components in the result array.
3171 * \param [in] func - the expression defining how to transform a tuple of \a this array.
3172 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
3173 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
3174 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
3175 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
3176 * same number of tuples as \a this array.
3177 * The caller is to delete this result array using decrRef() as it is no more
3179 * \throw If \a this is not allocated.
3180 * \throw If \a func contains vars that are not in \a this->getInfoOnComponent().
3181 * \throw If computing \a func fails.
3183 DataArrayDouble *DataArrayDouble::applyFuncCompo(int nbOfComp, const std::string& func, bool isSafe) const
3185 return applyFuncNamedCompo(nbOfComp,getVarsOnComponent(),func,isSafe);
3189 * Returns a new DataArrayDouble created from \a this one by applying a function to every
3190 * tuple of \a this array. Textual data is not copied.
3191 * For more info see \ref MEDCouplingArrayApplyFunc3.
3192 * \param [in] nbOfComp - number of components in the result array.
3193 * \param [in] varsOrder - sequence of vars defining their order.
3194 * \param [in] func - the expression defining how to transform a tuple of \a this array.
3195 * Supported expressions are described \ref MEDCouplingArrayApplyFuncExpr "here".
3196 * \param [in] isSafe - By default true. If true invalid operation (division by 0. acos of value > 1. ...) leads to a throw of an exception.
3197 * If false the computation is carried on without any notification. When false the evaluation is a little faster.
3198 * \return DataArrayDouble * - the new instance of DataArrayDouble containing the
3199 * same number of tuples as \a this array.
3200 * The caller is to delete this result array using decrRef() as it is no more
3202 * \throw If \a this is not allocated.
3203 * \throw If \a func contains vars not in \a varsOrder.
3204 * \throw If computing \a func fails.
3206 DataArrayDouble *DataArrayDouble::applyFuncNamedCompo(int nbOfComp, const std::vector<std::string>& varsOrder, const std::string& func, bool isSafe) const
3209 throw INTERP_KERNEL::Exception("DataArrayDouble::applyFuncNamedCompo : output number of component must be > 0 !");
3210 std::vector<std::string> varsOrder2(varsOrder);
3211 int oldNbOfComp(getNumberOfComponents());
3212 for(int i=(int)varsOrder.size();i<oldNbOfComp;i++)
3213 varsOrder2.push_back(std::string());
3215 int nbOfTuples(getNumberOfTuples());
3216 INTERP_KERNEL::ExprParser expr(func);
3218 std::set<std::string> vars;
3219 expr.getTrueSetOfVars(vars);
3220 if((int)vars.size()>oldNbOfComp)
3222 std::ostringstream oss; oss << "The field has " << oldNbOfComp << " components and there are ";
3223 oss << vars.size() << " variables : ";
3224 std::copy(vars.begin(),vars.end(),std::ostream_iterator<std::string>(oss," "));
3225 throw INTERP_KERNEL::Exception(oss.str().c_str());
3227 MCAuto<DataArrayDouble> newArr(DataArrayDouble::New());
3228 newArr->alloc(nbOfTuples,nbOfComp);
3229 INTERP_KERNEL::AutoPtr<double> buff(new double[oldNbOfComp]);
3230 double *buffPtr(buff),*ptrToFill;
3231 std::vector<double> stck;
3232 for(int iComp=0;iComp<nbOfComp;iComp++)
3234 expr.prepareExprEvaluationDouble(varsOrder2,oldNbOfComp,nbOfComp,iComp,buffPtr,buffPtr+oldNbOfComp);
3235 expr.prepareFastEvaluator();
3236 const double *ptr(getConstPointer());
3237 ptrToFill=newArr->getPointer()+iComp;
3240 for(int i=0;i<nbOfTuples;i++,ptrToFill+=nbOfComp,ptr+=oldNbOfComp)
3242 std::copy(ptr,ptr+oldNbOfComp,buffPtr);
3243 expr.evaluateDoubleInternal(stck);
3244 *ptrToFill=stck.back();
3250 for(int i=0;i<nbOfTuples;i++,ptrToFill+=nbOfComp,ptr+=oldNbOfComp)
3252 std::copy(ptr,ptr+oldNbOfComp,buffPtr);
3255 expr.evaluateDoubleInternalSafe(stck);
3256 *ptrToFill=stck.back();
3259 catch(INTERP_KERNEL::Exception& e)
3261 std::ostringstream oss; oss << "For tuple # " << i << " with value (";
3262 std::copy(ptr+oldNbOfComp*i,ptr+oldNbOfComp*(i+1),std::ostream_iterator<double>(oss,", "));
3263 oss << ") : Evaluation of function failed !" << e.what();
3264 throw INTERP_KERNEL::Exception(oss.str().c_str());
3269 return newArr.retn();
3272 void DataArrayDouble::applyFuncFast32(const std::string& func)
3275 INTERP_KERNEL::ExprParser expr(func);
3277 char *funcStr=expr.compileX86();
3279 *((void **)&funcPtr)=funcStr;//he he...
3281 double *ptr=getPointer();
3282 int nbOfComp=getNumberOfComponents();
3283 int nbOfTuples=getNumberOfTuples();
3284 int nbOfElems=nbOfTuples*nbOfComp;
3285 for(int i=0;i<nbOfElems;i++,ptr++)
3290 void DataArrayDouble::applyFuncFast64(const std::string& func)
3293 INTERP_KERNEL::ExprParser expr(func);
3295 char *funcStr=expr.compileX86_64();
3297 *((void **)&funcPtr)=funcStr;//he he...
3299 double *ptr=getPointer();
3300 int nbOfComp=getNumberOfComponents();
3301 int nbOfTuples=getNumberOfTuples();
3302 int nbOfElems=nbOfTuples*nbOfComp;
3303 for(int i=0;i<nbOfElems;i++,ptr++)
3309 * \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.
3311 MCAuto<DataArrayDouble> DataArrayDouble::symmetry3DPlane(const double point[3], const double normalVector[3]) const
3314 if(getNumberOfComponents()!=3)
3315 throw INTERP_KERNEL::Exception("DataArrayDouble::symmetry3DPlane : this is excepted to have 3 components !");
3316 int nbTuples(getNumberOfTuples());
3317 MCAuto<DataArrayDouble> ret(DataArrayDouble::New());
3318 ret->alloc(nbTuples,3);
3319 Symmetry3DPlane(point,normalVector,nbTuples,begin(),ret->getPointer());
3323 DataArrayDoubleIterator *DataArrayDouble::iterator()
3325 return new DataArrayDoubleIterator(this);
3329 * Returns a new DataArrayInt contating indices of tuples of \a this one-dimensional
3330 * array whose values are within a given range. Textual data is not copied.
3331 * \param [in] vmin - a lowest acceptable value (included).
3332 * \param [in] vmax - a greatest acceptable value (included).
3333 * \return DataArrayInt * - the new instance of DataArrayInt.
3334 * The caller is to delete this result array using decrRef() as it is no more
3336 * \throw If \a this->getNumberOfComponents() != 1.
3338 * \sa DataArrayDouble::findIdsNotInRange
3340 * \if ENABLE_EXAMPLES
3341 * \ref cpp_mcdataarraydouble_getidsinrange "Here is a C++ example".<br>
3342 * \ref py_mcdataarraydouble_getidsinrange "Here is a Python example".
3345 DataArrayInt *DataArrayDouble::findIdsInRange(double vmin, double vmax) const
3348 if(getNumberOfComponents()!=1)
3349 throw INTERP_KERNEL::Exception("DataArrayDouble::findIdsInRange : this must have exactly one component !");
3350 const double *cptr(begin());
3351 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
3352 int nbOfTuples(getNumberOfTuples());
3353 for(int i=0;i<nbOfTuples;i++,cptr++)
3354 if(*cptr>=vmin && *cptr<=vmax)
3355 ret->pushBackSilent(i);
3360 * Returns a new DataArrayInt contating indices of tuples of \a this one-dimensional
3361 * array whose values are not within a given range. Textual data is not copied.
3362 * \param [in] vmin - a lowest not acceptable value (excluded).
3363 * \param [in] vmax - a greatest not acceptable value (excluded).
3364 * \return DataArrayInt * - the new instance of DataArrayInt.
3365 * The caller is to delete this result array using decrRef() as it is no more
3367 * \throw If \a this->getNumberOfComponents() != 1.
3369 * \sa DataArrayDouble::findIdsInRange
3371 DataArrayInt *DataArrayDouble::findIdsNotInRange(double vmin, double vmax) const
3374 if(getNumberOfComponents()!=1)
3375 throw INTERP_KERNEL::Exception("DataArrayDouble::findIdsNotInRange : this must have exactly one component !");
3376 const double *cptr(begin());
3377 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
3378 int nbOfTuples(getNumberOfTuples());
3379 for(int i=0;i<nbOfTuples;i++,cptr++)
3380 if(*cptr<vmin || *cptr>vmax)
3381 ret->pushBackSilent(i);
3386 * Returns a new DataArrayDouble by concatenating two given arrays, so that (1) the number
3387 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
3388 * the number of component in the result array is same as that of each of given arrays.
3389 * Info on components is copied from the first of the given arrays. Number of components
3390 * in the given arrays must be the same.
3391 * \param [in] a1 - an array to include in the result array.
3392 * \param [in] a2 - another array to include in the result array.
3393 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3394 * The caller is to delete this result array using decrRef() as it is no more
3396 * \throw If both \a a1 and \a a2 are NULL.
3397 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents().
3399 DataArrayDouble *DataArrayDouble::Aggregate(const DataArrayDouble *a1, const DataArrayDouble *a2)
3401 std::vector<const DataArrayDouble *> tmp(2);
3402 tmp[0]=a1; tmp[1]=a2;
3403 return Aggregate(tmp);
3407 * Returns a new DataArrayDouble by concatenating all given arrays, so that (1) the number
3408 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
3409 * the number of component in the result array is same as that of each of given arrays.
3410 * Info on components is copied from the first of the given arrays. Number of components
3411 * in the given arrays must be the same.
3412 * If the number of non null of elements in \a arr is equal to one the returned object is a copy of it
3413 * not the object itself.
3414 * \param [in] arr - a sequence of arrays to include in the result array.
3415 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3416 * The caller is to delete this result array using decrRef() as it is no more
3418 * \throw If all arrays within \a arr are NULL.
3419 * \throw If getNumberOfComponents() of arrays within \a arr.
3421 DataArrayDouble *DataArrayDouble::Aggregate(const std::vector<const DataArrayDouble *>& arr)
3423 std::vector<const DataArrayDouble *> a;
3424 for(std::vector<const DataArrayDouble *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
3428 throw INTERP_KERNEL::Exception("DataArrayDouble::Aggregate : input list must contain at least one NON EMPTY DataArrayDouble !");
3429 std::vector<const DataArrayDouble *>::const_iterator it=a.begin();
3430 int nbOfComp=(*it)->getNumberOfComponents();
3431 int nbt=(*it++)->getNumberOfTuples();
3432 for(int i=1;it!=a.end();it++,i++)
3434 if((*it)->getNumberOfComponents()!=nbOfComp)
3435 throw INTERP_KERNEL::Exception("DataArrayDouble::Aggregate : Nb of components mismatch for array aggregation !");
3436 nbt+=(*it)->getNumberOfTuples();
3438 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
3439 ret->alloc(nbt,nbOfComp);
3440 double *pt=ret->getPointer();
3441 for(it=a.begin();it!=a.end();it++)
3442 pt=std::copy((*it)->getConstPointer(),(*it)->getConstPointer()+(*it)->getNbOfElems(),pt);
3443 ret->copyStringInfoFrom(*(a[0]));
3448 * Returns a new DataArrayDouble by aggregating two given arrays, so that (1) the number
3449 * of components in the result array is a sum of the number of components of given arrays
3450 * and (2) the number of tuples in the result array is same as that of each of given
3451 * arrays. In other words the i-th tuple of result array includes all components of
3452 * i-th tuples of all given arrays.
3453 * Number of tuples in the given arrays must be the same.
3454 * \param [in] a1 - an array to include in the result array.
3455 * \param [in] a2 - another array to include in the result array.
3456 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3457 * The caller is to delete this result array using decrRef() as it is no more
3459 * \throw If both \a a1 and \a a2 are NULL.
3460 * \throw If any given array is not allocated.
3461 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3463 DataArrayDouble *DataArrayDouble::Meld(const DataArrayDouble *a1, const DataArrayDouble *a2)
3465 std::vector<const DataArrayDouble *> arr(2);
3466 arr[0]=a1; arr[1]=a2;
3471 * Returns a new DataArrayDouble by aggregating all given arrays, so that (1) the number
3472 * of components in the result array is a sum of the number of components of given arrays
3473 * and (2) the number of tuples in the result array is same as that of each of given
3474 * arrays. In other words the i-th tuple of result array includes all components of
3475 * i-th tuples of all given arrays.
3476 * Number of tuples in the given arrays must be the same.
3477 * \param [in] arr - a sequence of arrays to include in the result array.
3478 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3479 * The caller is to delete this result array using decrRef() as it is no more
3481 * \throw If all arrays within \a arr are NULL.
3482 * \throw If any given array is not allocated.
3483 * \throw If getNumberOfTuples() of arrays within \a arr is different.
3485 DataArrayDouble *DataArrayDouble::Meld(const std::vector<const DataArrayDouble *>& arr)
3487 std::vector<const DataArrayDouble *> a;
3488 for(std::vector<const DataArrayDouble *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
3492 throw INTERP_KERNEL::Exception("DataArrayDouble::Meld : input list must contain at least one NON EMPTY DataArrayDouble !");
3493 std::vector<const DataArrayDouble *>::const_iterator it;
3494 for(it=a.begin();it!=a.end();it++)
3495 (*it)->checkAllocated();
3497 int nbOfTuples=(*it)->getNumberOfTuples();
3498 std::vector<int> nbc(a.size());
3499 std::vector<const double *> pts(a.size());
3500 nbc[0]=(*it)->getNumberOfComponents();
3501 pts[0]=(*it++)->getConstPointer();
3502 for(int i=1;it!=a.end();it++,i++)
3504 if(nbOfTuples!=(*it)->getNumberOfTuples())
3505 throw INTERP_KERNEL::Exception("DataArrayDouble::Meld : mismatch of number of tuples !");
3506 nbc[i]=(*it)->getNumberOfComponents();
3507 pts[i]=(*it)->getConstPointer();
3509 int totalNbOfComp=std::accumulate(nbc.begin(),nbc.end(),0);
3510 DataArrayDouble *ret=DataArrayDouble::New();
3511 ret->alloc(nbOfTuples,totalNbOfComp);
3512 double *retPtr=ret->getPointer();
3513 for(int i=0;i<nbOfTuples;i++)
3514 for(int j=0;j<(int)a.size();j++)
3516 retPtr=std::copy(pts[j],pts[j]+nbc[j],retPtr);
3520 for(int i=0;i<(int)a.size();i++)
3521 for(int j=0;j<nbc[i];j++,k++)
3522 ret->setInfoOnComponent(k,a[i]->getInfoOnComponent(j));
3527 * Returns a new DataArrayDouble containing a dot product of two given arrays, so that
3528 * the i-th tuple of the result array is a sum of products of j-th components of i-th
3529 * tuples of given arrays (\f$ a_i = \sum_{j=1}^n a1_j * a2_j \f$).
3530 * Info on components and name is copied from the first of the given arrays.
3531 * Number of tuples and components in the given arrays must be the same.
3532 * \param [in] a1 - a given array.
3533 * \param [in] a2 - another given array.
3534 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3535 * The caller is to delete this result array using decrRef() as it is no more
3537 * \throw If either \a a1 or \a a2 is NULL.
3538 * \throw If any given array is not allocated.
3539 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3540 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents()
3542 DataArrayDouble *DataArrayDouble::Dot(const DataArrayDouble *a1, const DataArrayDouble *a2)
3545 throw INTERP_KERNEL::Exception("DataArrayDouble::Dot : input DataArrayDouble instance is NULL !");
3546 a1->checkAllocated();
3547 a2->checkAllocated();
3548 int nbOfComp=a1->getNumberOfComponents();
3549 if(nbOfComp!=a2->getNumberOfComponents())
3550 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Dot !");
3551 int nbOfTuple=a1->getNumberOfTuples();
3552 if(nbOfTuple!=a2->getNumberOfTuples())
3553 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Dot !");
3554 DataArrayDouble *ret=DataArrayDouble::New();
3555 ret->alloc(nbOfTuple,1);
3556 double *retPtr=ret->getPointer();
3557 const double *a1Ptr=a1->getConstPointer();
3558 const double *a2Ptr=a2->getConstPointer();
3559 for(int i=0;i<nbOfTuple;i++)
3562 for(int j=0;j<nbOfComp;j++)
3563 sum+=a1Ptr[i*nbOfComp+j]*a2Ptr[i*nbOfComp+j];
3566 ret->setInfoOnComponent(0,a1->getInfoOnComponent(0));
3567 ret->setName(a1->getName());
3572 * Returns a new DataArrayDouble containing a cross product of two given arrays, so that
3573 * the i-th tuple of the result array contains 3 components of a vector which is a cross
3574 * product of two vectors defined by the i-th tuples of given arrays.
3575 * Info on components is copied from the first of the given arrays.
3576 * Number of tuples in the given arrays must be the same.
3577 * Number of components in the given arrays must be 3.
3578 * \param [in] a1 - a given array.
3579 * \param [in] a2 - another given array.
3580 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3581 * The caller is to delete this result array using decrRef() as it is no more
3583 * \throw If either \a a1 or \a a2 is NULL.
3584 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3585 * \throw If \a a1->getNumberOfComponents() != 3
3586 * \throw If \a a2->getNumberOfComponents() != 3
3588 DataArrayDouble *DataArrayDouble::CrossProduct(const DataArrayDouble *a1, const DataArrayDouble *a2)
3591 throw INTERP_KERNEL::Exception("DataArrayDouble::CrossProduct : input DataArrayDouble instance is NULL !");
3592 int nbOfComp=a1->getNumberOfComponents();
3593 if(nbOfComp!=a2->getNumberOfComponents())
3594 throw INTERP_KERNEL::Exception("Nb of components mismatch for array crossProduct !");
3596 throw INTERP_KERNEL::Exception("Nb of components must be equal to 3 for array crossProduct !");
3597 int nbOfTuple=a1->getNumberOfTuples();
3598 if(nbOfTuple!=a2->getNumberOfTuples())
3599 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array crossProduct !");
3600 DataArrayDouble *ret=DataArrayDouble::New();
3601 ret->alloc(nbOfTuple,3);
3602 double *retPtr=ret->getPointer();
3603 const double *a1Ptr=a1->getConstPointer();
3604 const double *a2Ptr=a2->getConstPointer();
3605 for(int i=0;i<nbOfTuple;i++)
3607 retPtr[3*i]=a1Ptr[3*i+1]*a2Ptr[3*i+2]-a1Ptr[3*i+2]*a2Ptr[3*i+1];
3608 retPtr[3*i+1]=a1Ptr[3*i+2]*a2Ptr[3*i]-a1Ptr[3*i]*a2Ptr[3*i+2];
3609 retPtr[3*i+2]=a1Ptr[3*i]*a2Ptr[3*i+1]-a1Ptr[3*i+1]*a2Ptr[3*i];
3611 ret->copyStringInfoFrom(*a1);
3616 * Returns a new DataArrayDouble containing maximal values of two given arrays.
3617 * Info on components is copied from the first of the given arrays.
3618 * Number of tuples and components in the given arrays must be the same.
3619 * \param [in] a1 - an array to compare values with another one.
3620 * \param [in] a2 - another array to compare values with the first one.
3621 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3622 * The caller is to delete this result array using decrRef() as it is no more
3624 * \throw If either \a a1 or \a a2 is NULL.
3625 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3626 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents()
3628 DataArrayDouble *DataArrayDouble::Max(const DataArrayDouble *a1, const DataArrayDouble *a2)
3631 throw INTERP_KERNEL::Exception("DataArrayDouble::Max : input DataArrayDouble instance is NULL !");
3632 int nbOfComp=a1->getNumberOfComponents();
3633 if(nbOfComp!=a2->getNumberOfComponents())
3634 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Max !");
3635 int nbOfTuple=a1->getNumberOfTuples();
3636 if(nbOfTuple!=a2->getNumberOfTuples())
3637 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Max !");
3638 DataArrayDouble *ret=DataArrayDouble::New();
3639 ret->alloc(nbOfTuple,nbOfComp);
3640 double *retPtr=ret->getPointer();
3641 const double *a1Ptr=a1->getConstPointer();
3642 const double *a2Ptr=a2->getConstPointer();
3643 int nbElem=nbOfTuple*nbOfComp;
3644 for(int i=0;i<nbElem;i++)
3645 retPtr[i]=std::max(a1Ptr[i],a2Ptr[i]);
3646 ret->copyStringInfoFrom(*a1);
3651 * Returns a new DataArrayDouble containing minimal values of two given arrays.
3652 * Info on components is copied from the first of the given arrays.
3653 * Number of tuples and components in the given arrays must be the same.
3654 * \param [in] a1 - an array to compare values with another one.
3655 * \param [in] a2 - another array to compare values with the first one.
3656 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3657 * The caller is to delete this result array using decrRef() as it is no more
3659 * \throw If either \a a1 or \a a2 is NULL.
3660 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
3661 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents()
3663 DataArrayDouble *DataArrayDouble::Min(const DataArrayDouble *a1, const DataArrayDouble *a2)
3666 throw INTERP_KERNEL::Exception("DataArrayDouble::Min : input DataArrayDouble instance is NULL !");
3667 int nbOfComp=a1->getNumberOfComponents();
3668 if(nbOfComp!=a2->getNumberOfComponents())
3669 throw INTERP_KERNEL::Exception("Nb of components mismatch for array min !");
3670 int nbOfTuple=a1->getNumberOfTuples();
3671 if(nbOfTuple!=a2->getNumberOfTuples())
3672 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array min !");
3673 DataArrayDouble *ret=DataArrayDouble::New();
3674 ret->alloc(nbOfTuple,nbOfComp);
3675 double *retPtr=ret->getPointer();
3676 const double *a1Ptr=a1->getConstPointer();
3677 const double *a2Ptr=a2->getConstPointer();
3678 int nbElem=nbOfTuple*nbOfComp;
3679 for(int i=0;i<nbElem;i++)
3680 retPtr[i]=std::min(a1Ptr[i],a2Ptr[i]);
3681 ret->copyStringInfoFrom(*a1);
3686 * Returns a new DataArrayDouble that is a sum of two given arrays. There are 3
3688 * 1. The arrays have same number of tuples and components. Then each value of
3689 * the result array (_a_) is a sum of the corresponding values of \a a1 and \a a2,
3690 * i.e.: _a_ [ i, j ] = _a1_ [ i, j ] + _a2_ [ i, j ].
3691 * 2. The arrays have same number of tuples and one array, say _a2_, has one
3693 * _a_ [ i, j ] = _a1_ [ i, j ] + _a2_ [ i, 0 ].
3694 * 3. The arrays have same number of components and one array, say _a2_, has one
3696 * _a_ [ i, j ] = _a1_ [ i, j ] + _a2_ [ 0, j ].
3698 * Info on components is copied either from the first array (in the first case) or from
3699 * the array with maximal number of elements (getNbOfElems()).
3700 * \param [in] a1 - an array to sum up.
3701 * \param [in] a2 - another array to sum up.
3702 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3703 * The caller is to delete this result array using decrRef() as it is no more
3705 * \throw If either \a a1 or \a a2 is NULL.
3706 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
3707 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
3708 * none of them has number of tuples or components equal to 1.
3710 DataArrayDouble *DataArrayDouble::Add(const DataArrayDouble *a1, const DataArrayDouble *a2)
3713 throw INTERP_KERNEL::Exception("DataArrayDouble::Add : input DataArrayDouble instance is NULL !");
3714 int nbOfTuple=a1->getNumberOfTuples();
3715 int nbOfTuple2=a2->getNumberOfTuples();
3716 int nbOfComp=a1->getNumberOfComponents();
3717 int nbOfComp2=a2->getNumberOfComponents();
3718 MCAuto<DataArrayDouble> ret=0;
3719 if(nbOfTuple==nbOfTuple2)
3721 if(nbOfComp==nbOfComp2)
3723 ret=DataArrayDouble::New();
3724 ret->alloc(nbOfTuple,nbOfComp);
3725 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::plus<double>());
3726 ret->copyStringInfoFrom(*a1);
3730 int nbOfCompMin,nbOfCompMax;
3731 const DataArrayDouble *aMin, *aMax;
3732 if(nbOfComp>nbOfComp2)
3734 nbOfCompMin=nbOfComp2; nbOfCompMax=nbOfComp;
3739 nbOfCompMin=nbOfComp; nbOfCompMax=nbOfComp2;
3744 ret=DataArrayDouble::New();
3745 ret->alloc(nbOfTuple,nbOfCompMax);
3746 const double *aMinPtr=aMin->getConstPointer();
3747 const double *aMaxPtr=aMax->getConstPointer();
3748 double *res=ret->getPointer();
3749 for(int i=0;i<nbOfTuple;i++)
3750 res=std::transform(aMaxPtr+i*nbOfCompMax,aMaxPtr+(i+1)*nbOfCompMax,res,std::bind2nd(std::plus<double>(),aMinPtr[i]));
3751 ret->copyStringInfoFrom(*aMax);
3754 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Add !");
3757 else if((nbOfTuple==1 && nbOfTuple2>1) || (nbOfTuple>1 && nbOfTuple2==1))
3759 if(nbOfComp==nbOfComp2)
3761 int nbOfTupleMax=std::max(nbOfTuple,nbOfTuple2);
3762 const DataArrayDouble *aMin=nbOfTuple>nbOfTuple2?a2:a1;
3763 const DataArrayDouble *aMax=nbOfTuple>nbOfTuple2?a1:a2;
3764 const double *aMinPtr=aMin->getConstPointer(),*aMaxPtr=aMax->getConstPointer();
3765 ret=DataArrayDouble::New();
3766 ret->alloc(nbOfTupleMax,nbOfComp);
3767 double *res=ret->getPointer();
3768 for(int i=0;i<nbOfTupleMax;i++)
3769 res=std::transform(aMaxPtr+i*nbOfComp,aMaxPtr+(i+1)*nbOfComp,aMinPtr,res,std::plus<double>());
3770 ret->copyStringInfoFrom(*aMax);
3773 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Add !");
3776 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Add !");
3781 * Adds values of another DataArrayDouble to values of \a this one. There are 3
3783 * 1. The arrays have same number of tuples and components. Then each value of
3784 * \a other array is added to the corresponding value of \a this array, i.e.:
3785 * _a_ [ i, j ] += _other_ [ i, j ].
3786 * 2. The arrays have same number of tuples and \a other array has one component. Then
3787 * _a_ [ i, j ] += _other_ [ i, 0 ].
3788 * 3. The arrays have same number of components and \a other array has one tuple. Then
3789 * _a_ [ i, j ] += _a2_ [ 0, j ].
3791 * \param [in] other - an array to add to \a this one.
3792 * \throw If \a other is NULL.
3793 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
3794 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
3795 * \a other has number of both tuples and components not equal to 1.
3797 void DataArrayDouble::addEqual(const DataArrayDouble *other)
3800 throw INTERP_KERNEL::Exception("DataArrayDouble::addEqual : input DataArrayDouble instance is NULL !");
3801 const char *msg="Nb of tuples mismatch for DataArrayDouble::addEqual !";
3803 other->checkAllocated();
3804 int nbOfTuple=getNumberOfTuples();
3805 int nbOfTuple2=other->getNumberOfTuples();
3806 int nbOfComp=getNumberOfComponents();
3807 int nbOfComp2=other->getNumberOfComponents();
3808 if(nbOfTuple==nbOfTuple2)
3810 if(nbOfComp==nbOfComp2)
3812 std::transform(begin(),end(),other->begin(),getPointer(),std::plus<double>());
3814 else if(nbOfComp2==1)
3816 double *ptr=getPointer();
3817 const double *ptrc=other->getConstPointer();
3818 for(int i=0;i<nbOfTuple;i++)
3819 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::plus<double>(),*ptrc++));
3822 throw INTERP_KERNEL::Exception(msg);
3824 else if(nbOfTuple2==1)
3826 if(nbOfComp2==nbOfComp)
3828 double *ptr=getPointer();
3829 const double *ptrc=other->getConstPointer();
3830 for(int i=0;i<nbOfTuple;i++)
3831 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::plus<double>());
3834 throw INTERP_KERNEL::Exception(msg);
3837 throw INTERP_KERNEL::Exception(msg);
3842 * Returns a new DataArrayDouble that is a subtraction of two given arrays. There are 3
3844 * 1. The arrays have same number of tuples and components. Then each value of
3845 * the result array (_a_) is a subtraction of the corresponding values of \a a1 and
3846 * \a a2, i.e.: _a_ [ i, j ] = _a1_ [ i, j ] - _a2_ [ i, j ].
3847 * 2. The arrays have same number of tuples and one array, say _a2_, has one
3849 * _a_ [ i, j ] = _a1_ [ i, j ] - _a2_ [ i, 0 ].
3850 * 3. The arrays have same number of components and one array, say _a2_, has one
3852 * _a_ [ i, j ] = _a1_ [ i, j ] - _a2_ [ 0, j ].
3854 * Info on components is copied either from the first array (in the first case) or from
3855 * the array with maximal number of elements (getNbOfElems()).
3856 * \param [in] a1 - an array to subtract from.
3857 * \param [in] a2 - an array to subtract.
3858 * \return DataArrayDouble * - the new instance of DataArrayDouble.
3859 * The caller is to delete this result array using decrRef() as it is no more
3861 * \throw If either \a a1 or \a a2 is NULL.
3862 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
3863 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
3864 * none of them has number of tuples or components equal to 1.
3866 DataArrayDouble *DataArrayDouble::Substract(const DataArrayDouble *a1, const DataArrayDouble *a2)
3869 throw INTERP_KERNEL::Exception("DataArrayDouble::Substract : input DataArrayDouble instance is NULL !");
3870 int nbOfTuple1=a1->getNumberOfTuples();
3871 int nbOfTuple2=a2->getNumberOfTuples();
3872 int nbOfComp1=a1->getNumberOfComponents();
3873 int nbOfComp2=a2->getNumberOfComponents();
3874 if(nbOfTuple2==nbOfTuple1)
3876 if(nbOfComp1==nbOfComp2)
3878 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
3879 ret->alloc(nbOfTuple2,nbOfComp1);
3880 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::minus<double>());
3881 ret->copyStringInfoFrom(*a1);
3884 else if(nbOfComp2==1)
3886 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
3887 ret->alloc(nbOfTuple1,nbOfComp1);
3888 const double *a2Ptr=a2->getConstPointer();
3889 const double *a1Ptr=a1->getConstPointer();
3890 double *res=ret->getPointer();
3891 for(int i=0;i<nbOfTuple1;i++)
3892 res=std::transform(a1Ptr+i*nbOfComp1,a1Ptr+(i+1)*nbOfComp1,res,std::bind2nd(std::minus<double>(),a2Ptr[i]));
3893 ret->copyStringInfoFrom(*a1);
3898 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Substract !");
3902 else if(nbOfTuple2==1)
3904 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Substract !");
3905 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
3906 ret->alloc(nbOfTuple1,nbOfComp1);
3907 const double *a1ptr=a1->getConstPointer(),*a2ptr=a2->getConstPointer();
3908 double *pt=ret->getPointer();
3909 for(int i=0;i<nbOfTuple1;i++)
3910 pt=std::transform(a1ptr+i*nbOfComp1,a1ptr+(i+1)*nbOfComp1,a2ptr,pt,std::minus<double>());
3911 ret->copyStringInfoFrom(*a1);
3916 a1->checkNbOfTuples(nbOfTuple2,"Nb of tuples mismatch for array Substract !");//will always throw an exception
3922 * Subtract values of another DataArrayDouble from values of \a this one. There are 3
3924 * 1. The arrays have same number of tuples and components. Then each value of
3925 * \a other array is subtracted from the corresponding value of \a this array, i.e.:
3926 * _a_ [ i, j ] -= _other_ [ i, j ].
3927 * 2. The arrays have same number of tuples and \a other array has one component. Then
3928 * _a_ [ i, j ] -= _other_ [ i, 0 ].
3929 * 3. The arrays have same number of components and \a other array has one tuple. Then
3930 * _a_ [ i, j ] -= _a2_ [ 0, j ].
3932 * \param [in] other - an array to subtract from \a this one.
3933 * \throw If \a other is NULL.
3934 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
3935 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
3936 * \a other has number of both tuples and components not equal to 1.
3938 void DataArrayDouble::substractEqual(const DataArrayDouble *other)
3941 throw INTERP_KERNEL::Exception("DataArrayDouble::substractEqual : input DataArrayDouble instance is NULL !");
3942 const char *msg="Nb of tuples mismatch for DataArrayDouble::substractEqual !";
3944 other->checkAllocated();
3945 int nbOfTuple=getNumberOfTuples();
3946 int nbOfTuple2=other->getNumberOfTuples();
3947 int nbOfComp=getNumberOfComponents();
3948 int nbOfComp2=other->getNumberOfComponents();
3949 if(nbOfTuple==nbOfTuple2)
3951 if(nbOfComp==nbOfComp2)
3953 std::transform(begin(),end(),other->begin(),getPointer(),std::minus<double>());
3955 else if(nbOfComp2==1)
3957 double *ptr=getPointer();
3958 const double *ptrc=other->getConstPointer();
3959 for(int i=0;i<nbOfTuple;i++)
3960 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::minus<double>(),*ptrc++));
3963 throw INTERP_KERNEL::Exception(msg);
3965 else if(nbOfTuple2==1)
3967 if(nbOfComp2==nbOfComp)
3969 double *ptr=getPointer();
3970 const double *ptrc=other->getConstPointer();
3971 for(int i=0;i<nbOfTuple;i++)
3972 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::minus<double>());
3975 throw INTERP_KERNEL::Exception(msg);
3978 throw INTERP_KERNEL::Exception(msg);
3983 * Returns a new DataArrayDouble that is a product of two given arrays. There are 3
3985 * 1. The arrays have same number of tuples and components. Then each value of
3986 * the result array (_a_) is a product of the corresponding values of \a a1 and
3987 * \a a2, i.e. _a_ [ i, j ] = _a1_ [ i, j ] * _a2_ [ i, j ].
3988 * 2. The arrays have same number of tuples and one array, say _a2_, has one
3990 * _a_ [ i, j ] = _a1_ [ i, j ] * _a2_ [ i, 0 ].
3991 * 3. The arrays have same number of components and one array, say _a2_, has one
3993 * _a_ [ i, j ] = _a1_ [ i, j ] * _a2_ [ 0, j ].
3995 * Info on components is copied either from the first array (in the first case) or from
3996 * the array with maximal number of elements (getNbOfElems()).
3997 * \param [in] a1 - a factor array.
3998 * \param [in] a2 - another factor array.
3999 * \return DataArrayDouble * - the new instance of DataArrayDouble.
4000 * The caller is to delete this result array using decrRef() as it is no more
4002 * \throw If either \a a1 or \a a2 is NULL.
4003 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
4004 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
4005 * none of them has number of tuples or components equal to 1.
4007 DataArrayDouble *DataArrayDouble::Multiply(const DataArrayDouble *a1, const DataArrayDouble *a2)
4010 throw INTERP_KERNEL::Exception("DataArrayDouble::Multiply : input DataArrayDouble instance is NULL !");
4011 int nbOfTuple=a1->getNumberOfTuples();
4012 int nbOfTuple2=a2->getNumberOfTuples();
4013 int nbOfComp=a1->getNumberOfComponents();
4014 int nbOfComp2=a2->getNumberOfComponents();
4015 MCAuto<DataArrayDouble> ret=0;
4016 if(nbOfTuple==nbOfTuple2)
4018 if(nbOfComp==nbOfComp2)
4020 ret=DataArrayDouble::New();
4021 ret->alloc(nbOfTuple,nbOfComp);
4022 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::multiplies<double>());
4023 ret->copyStringInfoFrom(*a1);
4027 int nbOfCompMin,nbOfCompMax;
4028 const DataArrayDouble *aMin, *aMax;
4029 if(nbOfComp>nbOfComp2)
4031 nbOfCompMin=nbOfComp2; nbOfCompMax=nbOfComp;
4036 nbOfCompMin=nbOfComp; nbOfCompMax=nbOfComp2;
4041 ret=DataArrayDouble::New();
4042 ret->alloc(nbOfTuple,nbOfCompMax);
4043 const double *aMinPtr=aMin->getConstPointer();
4044 const double *aMaxPtr=aMax->getConstPointer();
4045 double *res=ret->getPointer();
4046 for(int i=0;i<nbOfTuple;i++)
4047 res=std::transform(aMaxPtr+i*nbOfCompMax,aMaxPtr+(i+1)*nbOfCompMax,res,std::bind2nd(std::multiplies<double>(),aMinPtr[i]));
4048 ret->copyStringInfoFrom(*aMax);
4051 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Multiply !");
4054 else if((nbOfTuple==1 && nbOfTuple2>1) || (nbOfTuple>1 && nbOfTuple2==1))
4056 if(nbOfComp==nbOfComp2)
4058 int nbOfTupleMax=std::max(nbOfTuple,nbOfTuple2);
4059 const DataArrayDouble *aMin=nbOfTuple>nbOfTuple2?a2:a1;
4060 const DataArrayDouble *aMax=nbOfTuple>nbOfTuple2?a1:a2;
4061 const double *aMinPtr=aMin->getConstPointer(),*aMaxPtr=aMax->getConstPointer();
4062 ret=DataArrayDouble::New();
4063 ret->alloc(nbOfTupleMax,nbOfComp);
4064 double *res=ret->getPointer();
4065 for(int i=0;i<nbOfTupleMax;i++)
4066 res=std::transform(aMaxPtr+i*nbOfComp,aMaxPtr+(i+1)*nbOfComp,aMinPtr,res,std::multiplies<double>());
4067 ret->copyStringInfoFrom(*aMax);
4070 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Multiply !");
4073 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Multiply !");
4078 * Multiply values of another DataArrayDouble to values of \a this one. There are 3
4080 * 1. The arrays have same number of tuples and components. Then each value of
4081 * \a other array is multiplied to the corresponding value of \a this array, i.e.
4082 * _this_ [ i, j ] *= _other_ [ i, j ].
4083 * 2. The arrays have same number of tuples and \a other array has one component. Then
4084 * _this_ [ i, j ] *= _other_ [ i, 0 ].
4085 * 3. The arrays have same number of components and \a other array has one tuple. Then
4086 * _this_ [ i, j ] *= _a2_ [ 0, j ].
4088 * \param [in] other - an array to multiply to \a this one.
4089 * \throw If \a other is NULL.
4090 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
4091 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
4092 * \a other has number of both tuples and components not equal to 1.
4094 void DataArrayDouble::multiplyEqual(const DataArrayDouble *other)
4097 throw INTERP_KERNEL::Exception("DataArrayDouble::multiplyEqual : input DataArrayDouble instance is NULL !");
4098 const char *msg="Nb of tuples mismatch for DataArrayDouble::multiplyEqual !";
4100 other->checkAllocated();
4101 int nbOfTuple=getNumberOfTuples();
4102 int nbOfTuple2=other->getNumberOfTuples();
4103 int nbOfComp=getNumberOfComponents();
4104 int nbOfComp2=other->getNumberOfComponents();
4105 if(nbOfTuple==nbOfTuple2)
4107 if(nbOfComp==nbOfComp2)
4109 std::transform(begin(),end(),other->begin(),getPointer(),std::multiplies<double>());
4111 else if(nbOfComp2==1)
4113 double *ptr=getPointer();
4114 const double *ptrc=other->getConstPointer();
4115 for(int i=0;i<nbOfTuple;i++)
4116 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::multiplies<double>(),*ptrc++));
4119 throw INTERP_KERNEL::Exception(msg);
4121 else if(nbOfTuple2==1)
4123 if(nbOfComp2==nbOfComp)
4125 double *ptr=getPointer();
4126 const double *ptrc=other->getConstPointer();
4127 for(int i=0;i<nbOfTuple;i++)
4128 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::multiplies<double>());
4131 throw INTERP_KERNEL::Exception(msg);
4134 throw INTERP_KERNEL::Exception(msg);
4139 * Returns a new DataArrayDouble that is a division of two given arrays. There are 3
4141 * 1. The arrays have same number of tuples and components. Then each value of
4142 * the result array (_a_) is a division of the corresponding values of \a a1 and
4143 * \a a2, i.e.: _a_ [ i, j ] = _a1_ [ i, j ] / _a2_ [ i, j ].
4144 * 2. The arrays have same number of tuples and one array, say _a2_, has one
4146 * _a_ [ i, j ] = _a1_ [ i, j ] / _a2_ [ i, 0 ].
4147 * 3. The arrays have same number of components and one array, say _a2_, has one
4149 * _a_ [ i, j ] = _a1_ [ i, j ] / _a2_ [ 0, j ].
4151 * Info on components is copied either from the first array (in the first case) or from
4152 * the array with maximal number of elements (getNbOfElems()).
4153 * \warning No check of division by zero is performed!
4154 * \param [in] a1 - a numerator array.
4155 * \param [in] a2 - a denominator array.
4156 * \return DataArrayDouble * - the new instance of DataArrayDouble.
4157 * The caller is to delete this result array using decrRef() as it is no more
4159 * \throw If either \a a1 or \a a2 is NULL.
4160 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
4161 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
4162 * none of them has number of tuples or components equal to 1.
4164 DataArrayDouble *DataArrayDouble::Divide(const DataArrayDouble *a1, const DataArrayDouble *a2)
4167 throw INTERP_KERNEL::Exception("DataArrayDouble::Divide : input DataArrayDouble instance is NULL !");
4168 int nbOfTuple1=a1->getNumberOfTuples();
4169 int nbOfTuple2=a2->getNumberOfTuples();
4170 int nbOfComp1=a1->getNumberOfComponents();
4171 int nbOfComp2=a2->getNumberOfComponents();
4172 if(nbOfTuple2==nbOfTuple1)
4174 if(nbOfComp1==nbOfComp2)
4176 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
4177 ret->alloc(nbOfTuple2,nbOfComp1);
4178 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::divides<double>());
4179 ret->copyStringInfoFrom(*a1);
4182 else if(nbOfComp2==1)
4184 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
4185 ret->alloc(nbOfTuple1,nbOfComp1);
4186 const double *a2Ptr=a2->getConstPointer();
4187 const double *a1Ptr=a1->getConstPointer();
4188 double *res=ret->getPointer();
4189 for(int i=0;i<nbOfTuple1;i++)
4190 res=std::transform(a1Ptr+i*nbOfComp1,a1Ptr+(i+1)*nbOfComp1,res,std::bind2nd(std::divides<double>(),a2Ptr[i]));
4191 ret->copyStringInfoFrom(*a1);
4196 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Divide !");
4200 else if(nbOfTuple2==1)
4202 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Divide !");
4203 MCAuto<DataArrayDouble> ret=DataArrayDouble::New();
4204 ret->alloc(nbOfTuple1,nbOfComp1);
4205 const double *a1ptr=a1->getConstPointer(),*a2ptr=a2->getConstPointer();
4206 double *pt=ret->getPointer();
4207 for(int i=0;i<nbOfTuple1;i++)
4208 pt=std::transform(a1ptr+i*nbOfComp1,a1ptr+(i+1)*nbOfComp1,a2ptr,pt,std::divides<double>());
4209 ret->copyStringInfoFrom(*a1);
4214 a1->checkNbOfTuples(nbOfTuple2,"Nb of tuples mismatch for array Divide !");//will always throw an exception
4220 * Divide values of \a this array by values of another DataArrayDouble. There are 3
4222 * 1. The arrays have same number of tuples and components. Then each value of
4223 * \a this array is divided by the corresponding value of \a other one, i.e.:
4224 * _a_ [ i, j ] /= _other_ [ i, j ].
4225 * 2. The arrays have same number of tuples and \a other array has one component. Then
4226 * _a_ [ i, j ] /= _other_ [ i, 0 ].
4227 * 3. The arrays have same number of components and \a other array has one tuple. Then
4228 * _a_ [ i, j ] /= _a2_ [ 0, j ].
4230 * \warning No check of division by zero is performed!
4231 * \param [in] other - an array to divide \a this one by.
4232 * \throw If \a other is NULL.
4233 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
4234 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
4235 * \a other has number of both tuples and components not equal to 1.
4237 void DataArrayDouble::divideEqual(const DataArrayDouble *other)
4240 throw INTERP_KERNEL::Exception("DataArrayDouble::divideEqual : input DataArrayDouble instance is NULL !");
4241 const char *msg="Nb of tuples mismatch for DataArrayDouble::divideEqual !";
4243 other->checkAllocated();
4244 int nbOfTuple=getNumberOfTuples();
4245 int nbOfTuple2=other->getNumberOfTuples();
4246 int nbOfComp=getNumberOfComponents();
4247 int nbOfComp2=other->getNumberOfComponents();
4248 if(nbOfTuple==nbOfTuple2)
4250 if(nbOfComp==nbOfComp2)
4252 std::transform(begin(),end(),other->begin(),getPointer(),std::divides<double>());
4254 else if(nbOfComp2==1)
4256 double *ptr=getPointer();
4257 const double *ptrc=other->getConstPointer();
4258 for(int i=0;i<nbOfTuple;i++)
4259 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::divides<double>(),*ptrc++));
4262 throw INTERP_KERNEL::Exception(msg);
4264 else if(nbOfTuple2==1)
4266 if(nbOfComp2==nbOfComp)
4268 double *ptr=getPointer();
4269 const double *ptrc=other->getConstPointer();
4270 for(int i=0;i<nbOfTuple;i++)
4271 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::divides<double>());
4274 throw INTERP_KERNEL::Exception(msg);
4277 throw INTERP_KERNEL::Exception(msg);
4282 * Returns a new DataArrayDouble that is the result of pow of two given arrays. There are 3
4285 * \param [in] a1 - an array to pow up.
4286 * \param [in] a2 - another array to sum up.
4287 * \return DataArrayDouble * - the new instance of DataArrayDouble.
4288 * The caller is to delete this result array using decrRef() as it is no more
4290 * \throw If either \a a1 or \a a2 is NULL.
4291 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
4292 * \throw If \a a1->getNumberOfComponents() != 1 or \a a2->getNumberOfComponents() != 1.
4293 * \throw If there is a negative value in \a a1.
4295 DataArrayDouble *DataArrayDouble::Pow(const DataArrayDouble *a1, const DataArrayDouble *a2)
4298 throw INTERP_KERNEL::Exception("DataArrayDouble::Pow : at least one of input instances is null !");
4299 int nbOfTuple=a1->getNumberOfTuples();
4300 int nbOfTuple2=a2->getNumberOfTuples();
4301 int nbOfComp=a1->getNumberOfComponents();
4302 int nbOfComp2=a2->getNumberOfComponents();
4303 if(nbOfTuple!=nbOfTuple2)
4304 throw INTERP_KERNEL::Exception("DataArrayDouble::Pow : number of tuples mismatches !");
4305 if(nbOfComp!=1 || nbOfComp2!=1)
4306 throw INTERP_KERNEL::Exception("DataArrayDouble::Pow : number of components of both arrays must be equal to 1 !");
4307 MCAuto<DataArrayDouble> ret=DataArrayDouble::New(); ret->alloc(nbOfTuple,1);
4308 const double *ptr1(a1->begin()),*ptr2(a2->begin());
4309 double *ptr=ret->getPointer();
4310 for(int i=0;i<nbOfTuple;i++,ptr1++,ptr2++,ptr++)
4314 *ptr=pow(*ptr1,*ptr2);
4318 std::ostringstream oss; oss << "DataArrayDouble::Pow : on tuple #" << i << " of a1 value is < 0 (" << *ptr1 << ") !";
4319 throw INTERP_KERNEL::Exception(oss.str().c_str());
4326 * Apply pow on values of another DataArrayDouble to values of \a this one.
4328 * \param [in] other - an array to pow to \a this one.
4329 * \throw If \a other is NULL.
4330 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples()
4331 * \throw If \a this->getNumberOfComponents() != 1 or \a other->getNumberOfComponents() != 1
4332 * \throw If there is a negative value in \a this.
4334 void DataArrayDouble::powEqual(const DataArrayDouble *other)
4337 throw INTERP_KERNEL::Exception("DataArrayDouble::powEqual : input instance is null !");
4338 int nbOfTuple=getNumberOfTuples();
4339 int nbOfTuple2=other->getNumberOfTuples();
4340 int nbOfComp=getNumberOfComponents();
4341 int nbOfComp2=other->getNumberOfComponents();
4342 if(nbOfTuple!=nbOfTuple2)
4343 throw INTERP_KERNEL::Exception("DataArrayDouble::powEqual : number of tuples mismatches !");
4344 if(nbOfComp!=1 || nbOfComp2!=1)
4345 throw INTERP_KERNEL::Exception("DataArrayDouble::powEqual : number of components of both arrays must be equal to 1 !");
4346 double *ptr=getPointer();
4347 const double *ptrc=other->begin();
4348 for(int i=0;i<nbOfTuple;i++,ptrc++,ptr++)
4351 *ptr=pow(*ptr,*ptrc);
4354 std::ostringstream oss; oss << "DataArrayDouble::powEqual : on tuple #" << i << " of this value is < 0 (" << *ptr << ") !";
4355 throw INTERP_KERNEL::Exception(oss.str().c_str());
4362 * This method is \b NOT wrapped into python because it can be useful only for performance reasons in C++ context.
4363 * All values in \a this must be 0. or 1. within eps error. 0 means false, 1 means true.
4364 * If an another value than 0 or 1 appear (within eps precision) an INTERP_KERNEL::Exception will be thrown.
4366 * \throw if \a this is not allocated.
4367 * \throw if \a this has not exactly one component.
4369 std::vector<bool> DataArrayDouble::toVectorOfBool(double eps) const
4372 if(getNumberOfComponents()!=1)
4373 throw INTERP_KERNEL::Exception("DataArrayDouble::toVectorOfBool : must be applied on single component array !");
4374 int nbt(getNumberOfTuples());
4375 std::vector<bool> ret(nbt);
4376 const double *pt(begin());
4377 for(int i=0;i<nbt;i++)
4381 else if(fabs(pt[i]-1.)<eps)
4385 std::ostringstream oss; oss << "DataArrayDouble::toVectorOfBool : the tuple #" << i << " has value " << pt[i] << " is invalid ! must be 0. or 1. !";
4386 throw INTERP_KERNEL::Exception(oss.str().c_str());
4393 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
4396 void DataArrayDouble::getTinySerializationIntInformation(std::vector<int>& tinyInfo) const
4401 tinyInfo[0]=getNumberOfTuples();
4402 tinyInfo[1]=getNumberOfComponents();
4412 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
4415 void DataArrayDouble::getTinySerializationStrInformation(std::vector<std::string>& tinyInfo) const
4419 int nbOfCompo=getNumberOfComponents();
4420 tinyInfo.resize(nbOfCompo+1);
4421 tinyInfo[0]=getName();
4422 for(int i=0;i<nbOfCompo;i++)
4423 tinyInfo[i+1]=getInfoOnComponent(i);
4428 tinyInfo[0]=getName();
4433 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
4434 * This method returns if a feeding is needed.
4436 bool DataArrayDouble::resizeForUnserialization(const std::vector<int>& tinyInfoI)
4438 int nbOfTuple=tinyInfoI[0];
4439 int nbOfComp=tinyInfoI[1];
4440 if(nbOfTuple!=-1 || nbOfComp!=-1)
4442 alloc(nbOfTuple,nbOfComp);
4449 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
4451 void DataArrayDouble::finishUnserialization(const std::vector<int>& tinyInfoI, const std::vector<std::string>& tinyInfoS)
4453 setName(tinyInfoS[0]);
4456 int nbOfCompo=getNumberOfComponents();
4457 for(int i=0;i<nbOfCompo;i++)
4458 setInfoOnComponent(i,tinyInfoS[i+1]);
4463 * Low static method that operates 3D rotation of 'nbNodes' 3D nodes whose coordinates are arranged in \a coordsIn
4464 * around an axe ( \a center, \a vect) and with angle \a angle.
4466 void DataArrayDouble::Rotate3DAlg(const double *center, const double *vect, double angle, int nbNodes, const double *coordsIn, double *coordsOut)
4468 if(!center || !vect)
4469 throw INTERP_KERNEL::Exception("DataArrayDouble::Rotate3DAlg : null vector in input !");
4470 double sina(sin(angle));
4471 double cosa(cos(angle));
4472 double vectorNorm[3];
4474 double matrixTmp[9];
4475 double norm(sqrt(vect[0]*vect[0]+vect[1]*vect[1]+vect[2]*vect[2]));
4476 if(norm<std::numeric_limits<double>::min())
4477 throw INTERP_KERNEL::Exception("DataArrayDouble::Rotate3DAlg : magnitude of input vector is too close of 0. !");
4478 std::transform(vect,vect+3,vectorNorm,std::bind2nd(std::multiplies<double>(),1/norm));
4479 //rotation matrix computation
4480 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;
4481 matrixTmp[0]=vectorNorm[0]*vectorNorm[0]; matrixTmp[1]=vectorNorm[0]*vectorNorm[1]; matrixTmp[2]=vectorNorm[0]*vectorNorm[2];
4482 matrixTmp[3]=vectorNorm[1]*vectorNorm[0]; matrixTmp[4]=vectorNorm[1]*vectorNorm[1]; matrixTmp[5]=vectorNorm[1]*vectorNorm[2];
4483 matrixTmp[6]=vectorNorm[2]*vectorNorm[0]; matrixTmp[7]=vectorNorm[2]*vectorNorm[1]; matrixTmp[8]=vectorNorm[2]*vectorNorm[2];
4484 std::transform(matrixTmp,matrixTmp+9,matrixTmp,std::bind2nd(std::multiplies<double>(),1-cosa));
4485 std::transform(matrix,matrix+9,matrixTmp,matrix,std::plus<double>());
4486 matrixTmp[0]=0.; matrixTmp[1]=-vectorNorm[2]; matrixTmp[2]=vectorNorm[1];
4487 matrixTmp[3]=vectorNorm[2]; matrixTmp[4]=0.; matrixTmp[5]=-vectorNorm[0];
4488 matrixTmp[6]=-vectorNorm[1]; matrixTmp[7]=vectorNorm[0]; matrixTmp[8]=0.;
4489 std::transform(matrixTmp,matrixTmp+9,matrixTmp,std::bind2nd(std::multiplies<double>(),sina));
4490 std::transform(matrix,matrix+9,matrixTmp,matrix,std::plus<double>());
4491 //rotation matrix computed.
4493 for(int i=0; i<nbNodes; i++)
4495 std::transform(coordsIn+i*3,coordsIn+(i+1)*3,center,tmp,std::minus<double>());
4496 coordsOut[i*3]=matrix[0]*tmp[0]+matrix[1]*tmp[1]+matrix[2]*tmp[2]+center[0];
4497 coordsOut[i*3+1]=matrix[3]*tmp[0]+matrix[4]*tmp[1]+matrix[5]*tmp[2]+center[1];
4498 coordsOut[i*3+2]=matrix[6]*tmp[0]+matrix[7]*tmp[1]+matrix[8]*tmp[2]+center[2];
4502 void DataArrayDouble::Symmetry3DPlane(const double point[3], const double normalVector[3], int nbNodes, const double *coordsIn, double *coordsOut)
4504 double matrix[9],matrix2[9],matrix3[9];
4505 double vect[3],crossVect[3];
4506 INTERP_KERNEL::orthogonalVect3(normalVector,vect);
4507 crossVect[0]=normalVector[1]*vect[2]-normalVector[2]*vect[1];
4508 crossVect[1]=normalVector[2]*vect[0]-normalVector[0]*vect[2];
4509 crossVect[2]=normalVector[0]*vect[1]-normalVector[1]*vect[0];
4510 double nv(INTERP_KERNEL::norm<3>(vect)),ni(INTERP_KERNEL::norm<3>(normalVector)),nc(INTERP_KERNEL::norm<3>(crossVect));
4511 matrix[0]=vect[0]/nv; matrix[1]=crossVect[0]/nc; matrix[2]=-normalVector[0]/ni;
4512 matrix[3]=vect[1]/nv; matrix[4]=crossVect[1]/nc; matrix[5]=-normalVector[1]/ni;
4513 matrix[6]=vect[2]/nv; matrix[7]=crossVect[2]/nc; matrix[8]=-normalVector[2]/ni;
4514 matrix2[0]=vect[0]/nv; matrix2[1]=vect[1]/nv; matrix2[2]=vect[2]/nv;
4515 matrix2[3]=crossVect[0]/nc; matrix2[4]=crossVect[1]/nc; matrix2[5]=crossVect[2]/nc;
4516 matrix2[6]=normalVector[0]/ni; matrix2[7]=normalVector[1]/ni; matrix2[8]=normalVector[2]/ni;
4517 for(int i=0;i<3;i++)
4518 for(int j=0;j<3;j++)
4521 for(int k=0;k<3;k++)
4522 val+=matrix[3*i+k]*matrix2[3*k+j];
4525 //rotation matrix computed.
4527 for(int i=0; i<nbNodes; i++)
4529 std::transform(coordsIn+i*3,coordsIn+(i+1)*3,point,tmp,std::minus<double>());
4530 coordsOut[i*3]=matrix3[0]*tmp[0]+matrix3[1]*tmp[1]+matrix3[2]*tmp[2]+point[0];
4531 coordsOut[i*3+1]=matrix3[3]*tmp[0]+matrix3[4]*tmp[1]+matrix3[5]*tmp[2]+point[1];
4532 coordsOut[i*3+2]=matrix3[6]*tmp[0]+matrix3[7]*tmp[1]+matrix3[8]*tmp[2]+point[2];
4536 void DataArrayDouble::GiveBaseForPlane(const double normalVector[3], double baseOfPlane[9])
4538 double vect[3],crossVect[3];
4539 INTERP_KERNEL::orthogonalVect3(normalVector,vect);
4540 crossVect[0]=normalVector[1]*vect[2]-normalVector[2]*vect[1];
4541 crossVect[1]=normalVector[2]*vect[0]-normalVector[0]*vect[2];
4542 crossVect[2]=normalVector[0]*vect[1]-normalVector[1]*vect[0];
4543 double nv(INTERP_KERNEL::norm<3>(vect)),ni(INTERP_KERNEL::norm<3>(normalVector)),nc(INTERP_KERNEL::norm<3>(crossVect));
4544 baseOfPlane[0]=vect[0]/nv; baseOfPlane[1]=vect[1]/nv; baseOfPlane[2]=vect[2]/nv;
4545 baseOfPlane[3]=crossVect[0]/nc; baseOfPlane[4]=crossVect[1]/nc; baseOfPlane[5]=crossVect[2]/nc;
4546 baseOfPlane[6]=normalVector[0]/ni; baseOfPlane[7]=normalVector[1]/ni; baseOfPlane[8]=normalVector[2]/ni;
4550 * Low static method that operates 3D rotation of \a nbNodes 3D nodes whose coordinates are arranged in \a coords
4551 * around the center point \a center and with angle \a angle.
4553 void DataArrayDouble::Rotate2DAlg(const double *center, double angle, int nbNodes, const double *coordsIn, double *coordsOut)
4555 double cosa=cos(angle);
4556 double sina=sin(angle);
4558 matrix[0]=cosa; matrix[1]=-sina; matrix[2]=sina; matrix[3]=cosa;
4560 for(int i=0; i<nbNodes; i++)
4562 std::transform(coordsIn+i*2,coordsIn+(i+1)*2,center,tmp,std::minus<double>());
4563 coordsOut[i*2]=matrix[0]*tmp[0]+matrix[1]*tmp[1]+center[0];
4564 coordsOut[i*2+1]=matrix[2]*tmp[0]+matrix[3]*tmp[1]+center[1];
4568 DataArrayDoubleIterator::DataArrayDoubleIterator(DataArrayDouble *da):DataArrayIterator<double>(da)
4572 DataArrayDoubleTuple::DataArrayDoubleTuple(double *pt, int nbOfComp):DataArrayTuple<double>(pt,nbOfComp)
4577 std::string DataArrayDoubleTuple::repr() const
4579 std::ostringstream oss; oss.precision(17); oss << "(";
4580 for(int i=0;i<_nb_of_compo-1;i++)
4581 oss << _pt[i] << ", ";
4582 oss << _pt[_nb_of_compo-1] << ")";
4586 double DataArrayDoubleTuple::doubleValue() const
4590 throw INTERP_KERNEL::Exception("DataArrayDoubleTuple::doubleValue : DataArrayDoubleTuple instance has not exactly 1 component -> Not possible to convert it into a double precision float !");
4594 * This method returns a newly allocated instance the caller should dealed with by a MEDCoupling::DataArrayDouble::decrRef.
4595 * This method performs \b no copy of data. The content is only referenced using MEDCoupling::DataArrayDouble::useArray with ownership set to \b false.
4596 * 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
4597 * \b nbOfCompo=1 and \bnbOfTuples==this->_nb_of_elem.
4599 DataArrayDouble *DataArrayDoubleTuple::buildDADouble(int nbOfTuples, int nbOfCompo) const
4601 if((_nb_of_compo==nbOfCompo && nbOfTuples==1) || (_nb_of_compo==nbOfTuples && nbOfCompo==1))
4603 DataArrayDouble *ret=DataArrayDouble::New();
4604 ret->useExternalArrayWithRWAccess(_pt,nbOfTuples,nbOfCompo);
4609 std::ostringstream oss; oss << "DataArrayDoubleTuple::buildDADouble : unable to build a requested DataArrayDouble instance with nbofTuple=" << nbOfTuples << " and nbOfCompo=" << nbOfCompo;
4610 oss << ".\nBecause the number of elements in this is " << _nb_of_compo << " !";
4611 throw INTERP_KERNEL::Exception(oss.str().c_str());
4616 * Returns a new instance of DataArrayInt. The caller is to delete this array
4617 * using decrRef() as it is no more needed.
4619 DataArrayInt *DataArrayInt::New()
4621 return new DataArrayInt;
4625 * Returns the only one value in \a this, if and only if number of elements
4626 * (nb of tuples * nb of components) is equal to 1, and that \a this is allocated.
4627 * \return double - the sole value stored in \a this array.
4628 * \throw If at least one of conditions stated above is not fulfilled.
4630 int DataArrayInt::intValue() const
4634 if(getNbOfElems()==1)
4636 return *getConstPointer();
4639 throw INTERP_KERNEL::Exception("DataArrayInt::intValue : DataArrayInt instance is allocated but number of elements is not equal to 1 !");
4642 throw INTERP_KERNEL::Exception("DataArrayInt::intValue : DataArrayInt instance is not allocated !");
4646 * Returns an integer value characterizing \a this array, which is useful for a quick
4647 * comparison of many instances of DataArrayInt.
4648 * \return int - the hash value.
4649 * \throw If \a this is not allocated.
4651 int DataArrayInt::getHashCode() const
4654 std::size_t nbOfElems=getNbOfElems();
4655 int ret=nbOfElems*65536;
4660 const int *pt=begin();
4661 for(std::size_t i=0;i<nbOfElems;i+=delta)
4662 ret0+=pt[i] & 0x1FFF;
4667 * Returns a full copy of \a this. For more info on copying data arrays see
4668 * \ref MEDCouplingArrayBasicsCopyDeep.
4669 * \return DataArrayInt * - a new instance of DataArrayInt.
4671 DataArrayInt *DataArrayInt::deepCopy() const
4673 return new DataArrayInt(*this);
4677 * Returns either a \a deep or \a shallow copy of this array. For more info see
4678 * \ref MEDCouplingArrayBasicsCopyDeep and \ref MEDCouplingArrayBasicsCopyShallow.
4679 * \param [in] dCpy - if \a true, a deep copy is returned, else, a shallow one.
4680 * \return DataArrayInt * - either a new instance of DataArrayInt (if \a dCpy
4681 * == \a true) or \a this instance (if \a dCpy == \a false).
4683 DataArrayInt *DataArrayInt::performCopyOrIncrRef(bool dCpy) const
4685 return DataArrayTemplateClassic<int>::PerformCopyOrIncrRef(dCpy,*this);
4689 * Assign zero to all values in \a this array. To know more on filling arrays see
4690 * \ref MEDCouplingArrayFill.
4691 * \throw If \a this is not allocated.
4693 void DataArrayInt::fillWithZero()
4699 * Set all values in \a this array so that the i-th element equals to \a init + i
4700 * (i starts from zero). To know more on filling arrays see \ref MEDCouplingArrayFill.
4701 * \param [in] init - value to assign to the first element of array.
4702 * \throw If \a this->getNumberOfComponents() != 1
4703 * \throw If \a this is not allocated.
4705 void DataArrayInt::iota(int init)
4708 if(getNumberOfComponents()!=1)
4709 throw INTERP_KERNEL::Exception("DataArrayInt::iota : works only for arrays with only one component, you can call 'rearrange' method before !");
4710 int *ptr=getPointer();
4711 int ntuples=getNumberOfTuples();
4712 for(int i=0;i<ntuples;i++)
4718 * Returns a textual and human readable representation of \a this instance of
4719 * DataArrayInt. This text is shown when a DataArrayInt is printed in Python.
4720 * \return std::string - text describing \a this DataArrayInt.
4722 * \sa reprNotTooLong, reprZip
4724 std::string DataArrayInt::repr() const
4726 std::ostringstream ret;
4731 std::string DataArrayInt::reprZip() const
4733 std::ostringstream ret;
4739 * This method is close to repr method except that when \a this has more than 1000 tuples, all tuples are not
4740 * printed out to avoid to consume too much space in interpretor.
4743 std::string DataArrayInt::reprNotTooLong() const
4745 std::ostringstream ret;
4746 reprNotTooLongStream(ret);
4750 void DataArrayInt::writeVTK(std::ostream& ofs, int indent, const std::string& type, const std::string& nameInFile, DataArrayByte *byteArr) const
4752 static const char SPACE[4]={' ',' ',' ',' '};
4754 std::string idt(indent,' ');
4755 ofs << idt << "<DataArray type=\"" << type << "\" Name=\"" << nameInFile << "\" NumberOfComponents=\"" << getNumberOfComponents() << "\"";
4758 ofs << " format=\"appended\" offset=\"" << byteArr->getNumberOfTuples() << "\">";
4759 if(std::string(type)=="Int32")
4761 const char *data(reinterpret_cast<const char *>(begin()));
4762 std::size_t sz(getNbOfElems()*sizeof(int));
4763 byteArr->insertAtTheEnd(data,data+sz);
4764 byteArr->insertAtTheEnd(SPACE,SPACE+4);
4766 else if(std::string(type)=="Int8")
4768 INTERP_KERNEL::AutoPtr<char> tmp(new char[getNbOfElems()]);
4769 std::copy(begin(),end(),(char *)tmp);
4770 byteArr->insertAtTheEnd((char *)tmp,(char *)tmp+getNbOfElems());
4771 byteArr->insertAtTheEnd(SPACE,SPACE+4);
4773 else if(std::string(type)=="UInt8")
4775 INTERP_KERNEL::AutoPtr<unsigned char> tmp(new unsigned char[getNbOfElems()]);
4776 std::copy(begin(),end(),(unsigned char *)tmp);
4777 byteArr->insertAtTheEnd((unsigned char *)tmp,(unsigned char *)tmp+getNbOfElems());
4778 byteArr->insertAtTheEnd(SPACE,SPACE+4);
4781 throw INTERP_KERNEL::Exception("DataArrayInt::writeVTK : Only Int32, Int8 and UInt8 supported !");
4785 ofs << " RangeMin=\"" << getMinValueInArray() << "\" RangeMax=\"" << getMaxValueInArray() << "\" format=\"ascii\">\n" << idt;
4786 std::copy(begin(),end(),std::ostream_iterator<int>(ofs," "));
4788 ofs << std::endl << idt << "</DataArray>\n";
4791 void DataArrayInt::reprStream(std::ostream& stream) const
4793 stream << "Name of int array : \"" << _name << "\"\n";
4794 reprWithoutNameStream(stream);
4797 void DataArrayInt::reprZipStream(std::ostream& stream) const
4799 stream << "Name of int array : \"" << _name << "\"\n";
4800 reprZipWithoutNameStream(stream);
4803 void DataArrayInt::reprNotTooLongStream(std::ostream& stream) const
4805 stream << "Name of int array : \"" << _name << "\"\n";
4806 reprNotTooLongWithoutNameStream(stream);
4809 void DataArrayInt::reprWithoutNameStream(std::ostream& stream) const
4811 DataArray::reprWithoutNameStream(stream);
4812 _mem.repr(getNumberOfComponents(),stream);
4815 void DataArrayInt::reprZipWithoutNameStream(std::ostream& stream) const
4817 DataArray::reprWithoutNameStream(stream);
4818 _mem.reprZip(getNumberOfComponents(),stream);
4821 void DataArrayInt::reprNotTooLongWithoutNameStream(std::ostream& stream) const
4823 DataArray::reprWithoutNameStream(stream);
4824 stream.precision(17);
4825 _mem.reprNotTooLong(getNumberOfComponents(),stream);
4828 void DataArrayInt::reprCppStream(const std::string& varName, std::ostream& stream) const
4830 int nbTuples=getNumberOfTuples(),nbComp=getNumberOfComponents();
4831 const int *data=getConstPointer();
4832 stream << "DataArrayInt *" << varName << "=DataArrayInt::New();" << std::endl;
4833 if(nbTuples*nbComp>=1)
4835 stream << "const int " << varName << "Data[" << nbTuples*nbComp << "]={";
4836 std::copy(data,data+nbTuples*nbComp-1,std::ostream_iterator<int>(stream,","));
4837 stream << data[nbTuples*nbComp-1] << "};" << std::endl;
4838 stream << varName << "->useArray(" << varName << "Data,false,CPP_DEALLOC," << nbTuples << "," << nbComp << ");" << std::endl;
4841 stream << varName << "->alloc(" << nbTuples << "," << nbComp << ");" << std::endl;
4842 stream << varName << "->setName(\"" << getName() << "\");" << std::endl;
4846 * Method that gives a quick overvien of \a this for python.
4848 void DataArrayInt::reprQuickOverview(std::ostream& stream) const
4850 static const std::size_t MAX_NB_OF_BYTE_IN_REPR=300;
4851 stream << "DataArrayInt C++ instance at " << this << ". ";
4854 int nbOfCompo=(int)_info_on_compo.size();
4857 int nbOfTuples=getNumberOfTuples();
4858 stream << "Number of tuples : " << nbOfTuples << ". Number of components : " << nbOfCompo << "." << std::endl;
4859 reprQuickOverviewData(stream,MAX_NB_OF_BYTE_IN_REPR);
4862 stream << "Number of components : 0.";
4865 stream << "*** No data allocated ****";
4868 void DataArrayInt::reprQuickOverviewData(std::ostream& stream, std::size_t maxNbOfByteInRepr) const
4870 const int *data=begin();
4871 int nbOfTuples=getNumberOfTuples();
4872 int nbOfCompo=(int)_info_on_compo.size();
4873 std::ostringstream oss2; oss2 << "[";
4874 std::string oss2Str(oss2.str());
4875 bool isFinished=true;
4876 for(int i=0;i<nbOfTuples && isFinished;i++)
4881 for(int j=0;j<nbOfCompo;j++,data++)
4884 if(j!=nbOfCompo-1) oss2 << ", ";
4890 if(i!=nbOfTuples-1) oss2 << ", ";
4891 std::string oss3Str(oss2.str());
4892 if(oss3Str.length()<maxNbOfByteInRepr)
4904 * Modifies in place \a this one-dimensional array so that each value \a v = \a indArrBg[ \a v ],
4905 * i.e. a current value is used as in index to get a new value from \a indArrBg.
4906 * \param [in] indArrBg - pointer to the first element of array of new values to assign
4908 * \param [in] indArrEnd - specifies the end of the array \a indArrBg, so that
4909 * the last value of \a indArrBg is \a indArrEnd[ -1 ].
4910 * \throw If \a this->getNumberOfComponents() != 1
4911 * \throw If any value of \a this can't be used as a valid index for
4912 * [\a indArrBg, \a indArrEnd).
4916 void DataArrayInt::transformWithIndArr(const int *indArrBg, const int *indArrEnd)
4919 if(getNumberOfComponents()!=1)
4920 throw INTERP_KERNEL::Exception("Call transformWithIndArr method on DataArrayInt with only one component, you can call 'rearrange' method before !");
4921 int nbElemsIn((int)std::distance(indArrBg,indArrEnd)),nbOfTuples(getNumberOfTuples()),*pt(getPointer());
4922 for(int i=0;i<nbOfTuples;i++,pt++)
4924 if(*pt>=0 && *pt<nbElemsIn)
4928 std::ostringstream oss; oss << "DataArrayInt::transformWithIndArr : error on tuple #" << i << " of this value is " << *pt << ", should be in [0," << nbElemsIn << ") !";
4929 throw INTERP_KERNEL::Exception(oss.str().c_str());
4936 * Computes distribution of values of \a this one-dimensional array between given value
4937 * ranges (casts). This method is typically useful for entity number spliting by types,
4939 * \warning The values contained in \a arrBg should be sorted ascendently. No
4940 * check of this is be done. If not, the result is not warranted.
4941 * \param [in] arrBg - the array of ascending values defining the value ranges. The i-th
4942 * value of \a arrBg (\a arrBg[ i ]) gives the lowest value of the i-th range,
4943 * and the greatest value of the i-th range equals to \a arrBg[ i+1 ] - 1. \a
4944 * arrBg containing \a n values defines \a n-1 ranges. The last value of \a arrBg
4945 * should be more than every value in \a this array.
4946 * \param [in] arrEnd - specifies the end of the array \a arrBg, so that
4947 * the last value of \a arrBg is \a arrEnd[ -1 ].
4948 * \param [out] castArr - a new instance of DataArrayInt, of same size as \a this array
4949 * (same number of tuples and components), the caller is to delete
4950 * using decrRef() as it is no more needed.
4951 * This array contains indices of ranges for every value of \a this array. I.e.
4952 * the i-th value of \a castArr gives the index of range the i-th value of \a this
4953 * belongs to. Or, in other words, this parameter contains for each tuple in \a
4954 * this in which cast it holds.
4955 * \param [out] rankInsideCast - a new instance of DataArrayInt, of same size as \a this
4956 * array, the caller is to delete using decrRef() as it is no more needed.
4957 * This array contains ranks of values of \a this array within ranges
4958 * they belongs to. I.e. the i-th value of \a rankInsideCast gives the rank of
4959 * the i-th value of \a this array within the \a castArr[ i ]-th range, to which
4960 * the i-th value of \a this belongs to. Or, in other words, this param contains
4961 * for each tuple its rank inside its cast. The rank is computed as difference
4962 * between the value and the lowest value of range.
4963 * \param [out] castsPresent - a new instance of DataArrayInt, containing indices of
4964 * ranges (casts) to which at least one value of \a this array belongs.
4965 * Or, in other words, this param contains the casts that \a this contains.
4966 * The caller is to delete this array using decrRef() as it is no more needed.
4968 * \b Example: If \a this contains [6,5,0,3,2,7,8,1,4] and \a arrBg contains [0,4,9] then
4969 * the output of this method will be :
4970 * - \a castArr : [1,1,0,0,0,1,1,0,1]
4971 * - \a rankInsideCast: [2,1,0,3,2,3,4,1,0]
4972 * - \a castsPresent : [0,1]
4974 * I.e. values of \a this array belong to 2 ranges: #0 and #1. Value 6 belongs to the
4975 * range #1 and its rank within this range is 2; etc.
4977 * \throw If \a this->getNumberOfComponents() != 1.
4978 * \throw If \a arrEnd - arrBg < 2.
4979 * \throw If any value of \a this is not less than \a arrEnd[-1].
4981 void DataArrayInt::splitByValueRange(const int *arrBg, const int *arrEnd,
4982 DataArrayInt *& castArr, DataArrayInt *& rankInsideCast, DataArrayInt *& castsPresent) const
4985 if(getNumberOfComponents()!=1)
4986 throw INTERP_KERNEL::Exception("Call splitByValueRange method on DataArrayInt with only one component, you can call 'rearrange' method before !");
4987 int nbOfTuples=getNumberOfTuples();
4988 std::size_t nbOfCast=std::distance(arrBg,arrEnd);
4990 throw INTERP_KERNEL::Exception("DataArrayInt::splitByValueRange : The input array giving the cast range values should be of size >=2 !");
4992 const int *work=getConstPointer();
4993 typedef std::reverse_iterator<const int *> rintstart;
4994 rintstart bg(arrEnd);//OK no problem because size of 'arr' is greater or equal 2
4995 rintstart end2(arrBg);
4996 MCAuto<DataArrayInt> ret1=DataArrayInt::New();
4997 MCAuto<DataArrayInt> ret2=DataArrayInt::New();
4998 MCAuto<DataArrayInt> ret3=DataArrayInt::New();
4999 ret1->alloc(nbOfTuples,1);
5000 ret2->alloc(nbOfTuples,1);
5001 int *ret1Ptr=ret1->getPointer();
5002 int *ret2Ptr=ret2->getPointer();
5003 std::set<std::size_t> castsDetected;
5004 for(int i=0;i<nbOfTuples;i++)
5006 rintstart res=std::find_if(bg,end2,std::bind2nd(std::less_equal<int>(), work[i]));
5007 std::size_t pos=std::distance(bg,res);
5008 std::size_t pos2=nbOfCast-pos;
5011 ret1Ptr[i]=(int)pos2;
5012 ret2Ptr[i]=work[i]-arrBg[pos2];
5013 castsDetected.insert(pos2);
5017 std::ostringstream oss; oss << "DataArrayInt::splitByValueRange : At rank #" << i << " the value is " << work[i] << " should be in [0," << *bg << ") !";
5018 throw INTERP_KERNEL::Exception(oss.str().c_str());
5021 ret3->alloc((int)castsDetected.size(),1);
5022 std::copy(castsDetected.begin(),castsDetected.end(),ret3->getPointer());
5023 castArr=ret1.retn();
5024 rankInsideCast=ret2.retn();
5025 castsPresent=ret3.retn();
5029 * 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 ).
5030 * 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 ).
5031 * This method works only if \a this is allocated and single component. If not an exception will be thrown.
5033 * \param [out] strt - the start of the range (included) if true is returned.
5034 * \param [out] sttoopp - the end of the range (not included) if true is returned.
5035 * \param [out] stteepp - the step of the range if true is returned.
5036 * \return the verdict of the check.
5038 * \sa DataArray::GetNumberOfItemGivenBES
5040 bool DataArrayInt::isRange(int& strt, int& sttoopp, int& stteepp) const
5043 if(getNumberOfComponents()!=1)
5044 throw INTERP_KERNEL::Exception("DataArrayInt::isRange : this must be single component array !");
5045 int nbTuples(getNumberOfTuples());
5047 { strt=0; sttoopp=0; stteepp=1; return true; }
5048 const int *pt(begin());
5051 { sttoopp=strt+1; stteepp=1; return true; }
5052 strt=*pt; sttoopp=pt[nbTuples-1];
5058 int a(sttoopp-1-strt),tmp(strt);
5059 if(a%(nbTuples-1)!=0)
5061 stteepp=a/(nbTuples-1);
5062 for(int i=0;i<nbTuples;i++,tmp+=stteepp)
5070 int a(strt-sttoopp-1),tmp(strt);
5071 if(a%(nbTuples-1)!=0)
5073 stteepp=-(a/(nbTuples-1));
5074 for(int i=0;i<nbTuples;i++,tmp+=stteepp)
5082 * Creates a one-dimensional DataArrayInt (\a res) whose contents are computed from
5083 * values of \a this (\a a) and the given (\a indArr) arrays as follows:
5084 * \a res[ \a indArr[ \a a[ i ]]] = i. I.e. for each value in place i \a v = \a a[ i ],
5085 * new value in place \a indArr[ \a v ] is i.
5086 * \param [in] indArrBg - the array holding indices within the result array to assign
5087 * indices of values of \a this array pointing to values of \a indArrBg.
5088 * \param [in] indArrEnd - specifies the end of the array \a indArrBg, so that
5089 * the last value of \a indArrBg is \a indArrEnd[ -1 ].
5090 * \return DataArrayInt * - the new instance of DataArrayInt.
5091 * The caller is to delete this result array using decrRef() as it is no more
5093 * \throw If \a this->getNumberOfComponents() != 1.
5094 * \throw If any value of \a this array is not a valid index for \a indArrBg array.
5095 * \throw If any value of \a indArrBg is not a valid index for \a this array.
5097 DataArrayInt *DataArrayInt::transformWithIndArrR(const int *indArrBg, const int *indArrEnd) const
5100 if(getNumberOfComponents()!=1)
5101 throw INTERP_KERNEL::Exception("Call transformWithIndArrR method on DataArrayInt with only one component, you can call 'rearrange' method before !");
5102 int nbElemsIn=(int)std::distance(indArrBg,indArrEnd);
5103 int nbOfTuples=getNumberOfTuples();
5104 const int *pt=getConstPointer();
5105 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5106 ret->alloc(nbOfTuples,1);
5107 ret->fillWithValue(-1);
5108 int *tmp=ret->getPointer();
5109 for(int i=0;i<nbOfTuples;i++,pt++)
5111 if(*pt>=0 && *pt<nbElemsIn)
5113 int pos=indArrBg[*pt];
5114 if(pos>=0 && pos<nbOfTuples)
5118 std::ostringstream oss; oss << "DataArrayInt::transformWithIndArrR : error on tuple #" << i << " value of new pos is " << pos << " ( indArrBg[" << *pt << "]) ! Should be in [0," << nbOfTuples << ") !";
5119 throw INTERP_KERNEL::Exception(oss.str().c_str());
5124 std::ostringstream oss; oss << "DataArrayInt::transformWithIndArrR : error on tuple #" << i << " value is " << *pt << " and indirectionnal array as a size equal to " << nbElemsIn << " !";
5125 throw INTERP_KERNEL::Exception(oss.str().c_str());
5132 * Creates a one-dimensional DataArrayInt of given length, whose contents are computed
5133 * from values of \a this array, which is supposed to contain a renumbering map in
5134 * "Old to New" mode. The result array contains a renumbering map in "New to Old" mode.
5135 * To know how to use the renumbering maps see \ref numbering.
5136 * \param [in] newNbOfElem - the number of tuples in the result array.
5137 * \return DataArrayInt * - the new instance of DataArrayInt.
5138 * The caller is to delete this result array using decrRef() as it is no more
5141 * \if ENABLE_EXAMPLES
5142 * \ref cpp_mcdataarrayint_invertarrayo2n2n2o "Here is a C++ example".<br>
5143 * \ref py_mcdataarrayint_invertarrayo2n2n2o "Here is a Python example".
5146 DataArrayInt *DataArrayInt::invertArrayO2N2N2O(int newNbOfElem) const
5148 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5149 ret->alloc(newNbOfElem,1);
5150 int nbOfOldNodes=getNumberOfTuples();
5151 const int *old2New=getConstPointer();
5152 int *pt=ret->getPointer();
5153 for(int i=0;i!=nbOfOldNodes;i++)
5155 int newp(old2New[i]);
5158 if(newp>=0 && newp<newNbOfElem)
5162 std::ostringstream oss; oss << "DataArrayInt::invertArrayO2N2N2O : At place #" << i << " the newplace is " << newp << " must be in [0," << newNbOfElem << ") !";
5163 throw INTERP_KERNEL::Exception(oss.str().c_str());
5171 * This method is similar to DataArrayInt::invertArrayO2N2N2O except that
5172 * 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]
5174 DataArrayInt *DataArrayInt::invertArrayO2N2N2OBis(int newNbOfElem) const
5176 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5177 ret->alloc(newNbOfElem,1);
5178 int nbOfOldNodes=getNumberOfTuples();
5179 const int *old2New=getConstPointer();
5180 int *pt=ret->getPointer();
5181 for(int i=nbOfOldNodes-1;i>=0;i--)
5183 int newp(old2New[i]);
5186 if(newp>=0 && newp<newNbOfElem)
5190 std::ostringstream oss; oss << "DataArrayInt::invertArrayO2N2N2OBis : At place #" << i << " the newplace is " << newp << " must be in [0," << newNbOfElem << ") !";
5191 throw INTERP_KERNEL::Exception(oss.str().c_str());
5199 * Creates a one-dimensional DataArrayInt of given length, whose contents are computed
5200 * from values of \a this array, which is supposed to contain a renumbering map in
5201 * "New to Old" mode. The result array contains a renumbering map in "Old to New" mode.
5202 * To know how to use the renumbering maps see \ref numbering.
5203 * \param [in] newNbOfElem - the number of tuples in the result array.
5204 * \return DataArrayInt * - the new instance of DataArrayInt.
5205 * The caller is to delete this result array using decrRef() as it is no more
5208 * \if ENABLE_EXAMPLES
5209 * \ref cpp_mcdataarrayint_invertarrayn2o2o2n "Here is a C++ example".
5211 * \ref py_mcdataarrayint_invertarrayn2o2o2n "Here is a Python example".
5214 DataArrayInt *DataArrayInt::invertArrayN2O2O2N(int oldNbOfElem) const
5217 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5218 ret->alloc(oldNbOfElem,1);
5219 const int *new2Old=getConstPointer();
5220 int *pt=ret->getPointer();
5221 std::fill(pt,pt+oldNbOfElem,-1);
5222 int nbOfNewElems=getNumberOfTuples();
5223 for(int i=0;i<nbOfNewElems;i++)
5226 if(v>=0 && v<oldNbOfElem)
5230 std::ostringstream oss; oss << "DataArrayInt::invertArrayN2O2O2N : in new id #" << i << " old value is " << v << " expected to be in [0," << oldNbOfElem << ") !";
5231 throw INTERP_KERNEL::Exception(oss.str().c_str());
5238 * Equivalent to DataArrayInt::isEqual except that if false the reason of
5239 * mismatch is given.
5241 * \param [in] other the instance to be compared with \a this
5242 * \param [out] reason In case of inequality returns the reason.
5243 * \sa DataArrayInt::isEqual
5245 bool DataArrayInt::isEqualIfNotWhy(const DataArrayInt& other, std::string& reason) const
5247 if(!areInfoEqualsIfNotWhy(other,reason))
5249 return _mem.isEqual(other._mem,0,reason);
5253 * Checks if \a this and another DataArrayInt are fully equal. For more info see
5254 * \ref MEDCouplingArrayBasicsCompare.
5255 * \param [in] other - an instance of DataArrayInt to compare with \a this one.
5256 * \return bool - \a true if the two arrays are equal, \a false else.
5258 bool DataArrayInt::isEqual(const DataArrayInt& other) const
5261 return isEqualIfNotWhy(other,tmp);
5265 * Checks if values of \a this and another DataArrayInt are equal. For more info see
5266 * \ref MEDCouplingArrayBasicsCompare.
5267 * \param [in] other - an instance of DataArrayInt to compare with \a this one.
5268 * \return bool - \a true if the values of two arrays are equal, \a false else.
5270 bool DataArrayInt::isEqualWithoutConsideringStr(const DataArrayInt& other) const
5273 return _mem.isEqual(other._mem,0,tmp);
5277 * Checks if values of \a this and another DataArrayInt are equal. Comparison is
5278 * performed on sorted value sequences.
5279 * For more info see\ref MEDCouplingArrayBasicsCompare.
5280 * \param [in] other - an instance of DataArrayInt to compare with \a this one.
5281 * \return bool - \a true if the sorted values of two arrays are equal, \a false else.
5283 bool DataArrayInt::isEqualWithoutConsideringStrAndOrder(const DataArrayInt& other) const
5285 MCAuto<DataArrayInt> a=deepCopy();
5286 MCAuto<DataArrayInt> b=other.deepCopy();
5289 return a->isEqualWithoutConsideringStr(*b);
5293 * This method compares content of input vector \a v and \a this.
5294 * 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.
5295 * For performance reasons \a this is expected to be sorted ascendingly. If not an exception will be thrown.
5297 * \param [in] v - the vector of 'flags' to be compared with \a this.
5299 * \throw If \a this is not sorted ascendingly.
5300 * \throw If \a this has not exactly one component.
5301 * \throw If \a this is not allocated.
5303 bool DataArrayInt::isFittingWith(const std::vector<bool>& v) const
5306 if(getNumberOfComponents()!=1)
5307 throw INTERP_KERNEL::Exception("DataArrayInt::isFittingWith : number of components of this should be equal to one !");
5308 const int *w(begin()),*end2(end());
5309 int refVal=-std::numeric_limits<int>::max();
5311 std::vector<bool>::const_iterator it(v.begin());
5312 for(;it!=v.end();it++,i++)
5324 std::ostringstream oss; oss << "DataArrayInt::isFittingWith : At pos #" << std::distance(begin(),w-1) << " this is not sorted ascendingly !";
5325 throw INTERP_KERNEL::Exception(oss.str().c_str());
5339 * 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
5340 * put True to the corresponding entry in \a vec.
5341 * \a vec is expected to be with the same size than the number of tuples of \a this.
5343 * \sa DataArrayInt::switchOnTupleNotEqualTo.
5345 void DataArrayInt::switchOnTupleEqualTo(int val, std::vector<bool>& vec) const
5348 if(getNumberOfComponents()!=1)
5349 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleEqualTo : number of components of this should be equal to one !");
5350 int nbOfTuples(getNumberOfTuples());
5351 if(nbOfTuples!=(int)vec.size())
5352 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleEqualTo : number of tuples of this should be equal to size of input vector of bool !");
5353 const int *pt(begin());
5354 for(int i=0;i<nbOfTuples;i++)
5360 * 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
5361 * put True to the corresponding entry in \a vec.
5362 * \a vec is expected to be with the same size than the number of tuples of \a this.
5364 * \sa DataArrayInt::switchOnTupleEqualTo.
5366 void DataArrayInt::switchOnTupleNotEqualTo(int val, std::vector<bool>& vec) const
5369 if(getNumberOfComponents()!=1)
5370 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleNotEqualTo : number of components of this should be equal to one !");
5371 int nbOfTuples(getNumberOfTuples());
5372 if(nbOfTuples!=(int)vec.size())
5373 throw INTERP_KERNEL::Exception("DataArrayInt::switchOnTupleNotEqualTo : number of tuples of this should be equal to size of input vector of bool !");
5374 const int *pt(begin());
5375 for(int i=0;i<nbOfTuples;i++)
5381 * Computes for each tuple the sum of number of components values in the tuple and return it.
5383 * \return DataArrayInt * - the new instance of DataArrayInt containing the
5384 * same number of tuples as \a this array and one component.
5385 * The caller is to delete this result array using decrRef() as it is no more
5387 * \throw If \a this is not allocated.
5389 DataArrayInt *DataArrayInt::sumPerTuple() const
5392 int nbOfComp(getNumberOfComponents()),nbOfTuple(getNumberOfTuples());
5393 MCAuto<DataArrayInt> ret(DataArrayInt::New());
5394 ret->alloc(nbOfTuple,1);
5395 const int *src(getConstPointer());
5396 int *dest(ret->getPointer());
5397 for(int i=0;i<nbOfTuple;i++,dest++,src+=nbOfComp)
5398 *dest=std::accumulate(src,src+nbOfComp,0);
5403 * Checks that \a this array is consistently **increasing** or **decreasing** in value.
5404 * If not an exception is thrown.
5405 * \param [in] increasing - if \a true, the array values should be increasing.
5406 * \throw If sequence of values is not strictly monotonic in agreement with \a
5408 * \throw If \a this->getNumberOfComponents() != 1.
5409 * \throw If \a this is not allocated.
5411 void DataArrayInt::checkMonotonic(bool increasing) const
5413 if(!isMonotonic(increasing))
5416 throw INTERP_KERNEL::Exception("DataArrayInt::checkMonotonic : 'this' is not INCREASING monotonic !");
5418 throw INTERP_KERNEL::Exception("DataArrayInt::checkMonotonic : 'this' is not DECREASING monotonic !");
5423 * Checks that \a this array is consistently **increasing** or **decreasing** in value.
5424 * \param [in] increasing - if \a true, array values should be increasing.
5425 * \return bool - \a true if values change in accordance with \a increasing arg.
5426 * \throw If \a this->getNumberOfComponents() != 1.
5427 * \throw If \a this is not allocated.
5429 bool DataArrayInt::isMonotonic(bool increasing) const
5432 if(getNumberOfComponents()!=1)
5433 throw INTERP_KERNEL::Exception("DataArrayInt::isMonotonic : only supported with 'this' array with ONE component !");
5434 int nbOfElements=getNumberOfTuples();
5435 const int *ptr=getConstPointer();
5441 for(int i=1;i<nbOfElements;i++)
5451 for(int i=1;i<nbOfElements;i++)
5463 * This method check that array consistently INCREASING or DECREASING in value.
5465 bool DataArrayInt::isStrictlyMonotonic(bool increasing) const
5468 if(getNumberOfComponents()!=1)
5469 throw INTERP_KERNEL::Exception("DataArrayInt::isStrictlyMonotonic : only supported with 'this' array with ONE component !");
5470 int nbOfElements=getNumberOfTuples();
5471 const int *ptr=getConstPointer();
5477 for(int i=1;i<nbOfElements;i++)
5487 for(int i=1;i<nbOfElements;i++)
5499 * This method check that array consistently INCREASING or DECREASING in value.
5501 void DataArrayInt::checkStrictlyMonotonic(bool increasing) const
5503 if(!isStrictlyMonotonic(increasing))
5506 throw INTERP_KERNEL::Exception("DataArrayInt::checkStrictlyMonotonic : 'this' is not strictly INCREASING monotonic !");
5508 throw INTERP_KERNEL::Exception("DataArrayInt::checkStrictlyMonotonic : 'this' is not strictly DECREASING monotonic !");
5513 * Creates a new one-dimensional DataArrayInt of the same size as \a this and a given
5514 * one-dimensional arrays that must be of the same length. The result array describes
5515 * correspondence between \a this and \a other arrays, so that
5516 * <em> other.getIJ(i,0) == this->getIJ(ret->getIJ(i),0)</em>. If such a permutation is
5517 * not possible because some element in \a other is not in \a this, an exception is thrown.
5518 * \param [in] other - an array to compute permutation to.
5519 * \return DataArrayInt * - a new instance of DataArrayInt, which is a permutation array
5520 * from \a this to \a other. The caller is to delete this array using decrRef() as it is
5522 * \throw If \a this->getNumberOfComponents() != 1.
5523 * \throw If \a other->getNumberOfComponents() != 1.
5524 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples().
5525 * \throw If \a other includes a value which is not in \a this array.
5527 * \if ENABLE_EXAMPLES
5528 * \ref cpp_mcdataarrayint_buildpermutationarr "Here is a C++ example".
5530 * \ref py_mcdataarrayint_buildpermutationarr "Here is a Python example".
5533 DataArrayInt *DataArrayInt::buildPermutationArr(const DataArrayInt& other) const
5536 if(getNumberOfComponents()!=1 || other.getNumberOfComponents()!=1)
5537 throw INTERP_KERNEL::Exception("DataArrayInt::buildPermutationArr : 'this' and 'other' have to have exactly ONE component !");
5538 int nbTuple=getNumberOfTuples();
5539 other.checkAllocated();
5540 if(nbTuple!=other.getNumberOfTuples())
5541 throw INTERP_KERNEL::Exception("DataArrayInt::buildPermutationArr : 'this' and 'other' must have the same number of tuple !");
5542 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5543 ret->alloc(nbTuple,1);
5544 ret->fillWithValue(-1);
5545 const int *pt=getConstPointer();
5546 std::map<int,int> mm;
5547 for(int i=0;i<nbTuple;i++)
5549 pt=other.getConstPointer();
5550 int *retToFill=ret->getPointer();
5551 for(int i=0;i<nbTuple;i++)
5553 std::map<int,int>::const_iterator it=mm.find(pt[i]);
5556 std::ostringstream oss; oss << "DataArrayInt::buildPermutationArr : Arrays mismatch : element (" << pt[i] << ") in 'other' not findable in 'this' !";
5557 throw INTERP_KERNEL::Exception(oss.str().c_str());
5559 retToFill[i]=(*it).second;
5565 * Elements of \a partOfThis are expected to be included in \a this.
5566 * The returned array \a ret is so that this[ret]==partOfThis
5568 * 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]
5569 * the return array will contain [3,2,5,7].
5571 * \a this is expected to be a 1 compo allocated array.
5572 * \param [in] partOfThis - A 1 compo allocated array
5573 * \return - A newly allocated array to be dealed by caller having the same number of tuples than \a partOfThis.
5574 * \throw if two same element is present twice in \a this
5575 * \throw if an element in \a partOfThis is \b NOT in \a this.
5577 DataArrayInt *DataArrayInt::indicesOfSubPart(const DataArrayInt& partOfThis) const
5579 if(getNumberOfComponents()!=1 || partOfThis.getNumberOfComponents()!=1)
5580 throw INTERP_KERNEL::Exception("DataArrayInt::indicesOfSubPart : this and input array must be one component array !");
5581 checkAllocated(); partOfThis.checkAllocated();
5582 int thisNbTuples(getNumberOfTuples()),nbTuples(partOfThis.getNumberOfTuples());
5583 const int *thisPt(begin()),*pt(partOfThis.begin());
5584 MCAuto<DataArrayInt> ret(DataArrayInt::New());
5585 ret->alloc(nbTuples,1);
5586 int *retPt(ret->getPointer());
5587 std::map<int,int> m;
5588 for(int i=0;i<thisNbTuples;i++,thisPt++)
5590 if(m.size()!=thisNbTuples)
5591 throw INTERP_KERNEL::Exception("DataArrayInt::indicesOfSubPart : some elements appears more than once !");
5592 for(int i=0;i<nbTuples;i++,retPt++,pt++)
5594 std::map<int,int>::const_iterator it(m.find(*pt));
5596 *retPt=(*it).second;
5599 std::ostringstream oss; oss << "DataArrayInt::indicesOfSubPart : At pos #" << i << " of input array value is " << *pt << " not in this !";
5600 throw INTERP_KERNEL::Exception(oss.str());
5606 void DataArrayInt::aggregate(const DataArrayInt *other)
5609 throw INTERP_KERNEL::Exception("DataArrayInt::aggregate : null pointer !");
5610 if(getNumberOfComponents()!=other->getNumberOfComponents())
5611 throw INTERP_KERNEL::Exception("DataArrayInt::aggregate : mismatch number of components !");
5612 _mem.insertAtTheEnd(other->begin(),other->end());
5616 * Returns a new DataArrayInt holding the same values as \a this array but differently
5617 * arranged in memory. If \a this array holds 2 components of 3 values:
5618 * \f$ x_0,x_1,x_2,y_0,y_1,y_2 \f$, then the result array holds these values arranged
5619 * as follows: \f$ x_0,y_0,x_1,y_1,x_2,y_2 \f$.
5620 * \warning Do not confuse this method with transpose()!
5621 * \return DataArrayInt * - the new instance of DataArrayInt that the caller
5622 * is to delete using decrRef() as it is no more needed.
5623 * \throw If \a this is not allocated.
5625 DataArrayInt *DataArrayInt::fromNoInterlace() const
5629 throw INTERP_KERNEL::Exception("DataArrayInt::fromNoInterlace : Not defined array !");
5630 int *tab=_mem.fromNoInterlace(getNumberOfComponents());
5631 DataArrayInt *ret=DataArrayInt::New();
5632 ret->useArray(tab,true,C_DEALLOC,getNumberOfTuples(),getNumberOfComponents());
5637 * Returns a new DataArrayInt holding the same values as \a this array but differently
5638 * arranged in memory. If \a this array holds 2 components of 3 values:
5639 * \f$ x_0,y_0,x_1,y_1,x_2,y_2 \f$, then the result array holds these values arranged
5640 * as follows: \f$ x_0,x_1,x_2,y_0,y_1,y_2 \f$.
5641 * \warning Do not confuse this method with transpose()!
5642 * \return DataArrayInt * - the new instance of DataArrayInt that the caller
5643 * is to delete using decrRef() as it is no more needed.
5644 * \throw If \a this is not allocated.
5646 DataArrayInt *DataArrayInt::toNoInterlace() const
5650 throw INTERP_KERNEL::Exception("DataArrayInt::toNoInterlace : Not defined array !");
5651 int *tab=_mem.toNoInterlace(getNumberOfComponents());
5652 DataArrayInt *ret=DataArrayInt::New();
5653 ret->useArray(tab,true,C_DEALLOC,getNumberOfTuples(),getNumberOfComponents());
5658 * Returns a new DataArrayInt containing a renumbering map in "Old to New" mode.
5659 * This map, if applied to \a this array, would make it sorted. For example, if
5660 * \a this array contents are [9,10,0,6,4,11,3,7] then the contents of the result array
5661 * are [5,6,0,3,2,7,1,4]; if this result array (\a res) is used as an argument in call
5662 * \a this->renumber(\a res) then the returned array contains [0,3,4,6,7,9,10,11].
5663 * This method is useful for renumbering (in MED file for example). For more info
5664 * on renumbering see \ref numbering.
5665 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5666 * array using decrRef() as it is no more needed.
5667 * \throw If \a this is not allocated.
5668 * \throw If \a this->getNumberOfComponents() != 1.
5669 * \throw If there are equal values in \a this array.
5671 DataArrayInt *DataArrayInt::checkAndPreparePermutation() const
5674 if(getNumberOfComponents()!=1)
5675 throw INTERP_KERNEL::Exception("DataArrayInt::checkAndPreparePermutation : number of components must == 1 !");
5676 int nbTuples=getNumberOfTuples();
5677 const int *pt=getConstPointer();
5678 int *pt2=CheckAndPreparePermutation(pt,pt+nbTuples);
5679 DataArrayInt *ret=DataArrayInt::New();
5680 ret->useArray(pt2,true,C_DEALLOC,nbTuples,1);
5685 * 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
5686 * input array \a ids2.
5687 * \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.
5688 * 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
5690 * In case of success (no throw) : \c ids1->renumber(ret)->isEqual(ids2) where \a ret is the return of this method.
5692 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5693 * array using decrRef() as it is no more needed.
5694 * \throw If either ids1 or ids2 is null not allocated or not with one components.
5697 DataArrayInt *DataArrayInt::FindPermutationFromFirstToSecond(const DataArrayInt *ids1, const DataArrayInt *ids2)
5700 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two input arrays must be not null !");
5701 if(!ids1->isAllocated() || !ids2->isAllocated())
5702 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two input arrays must be allocated !");
5703 if(ids1->getNumberOfComponents()!=1 || ids2->getNumberOfComponents()!=1)
5704 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two input arrays have exactly one component !");
5705 if(ids1->getNumberOfTuples()!=ids2->getNumberOfTuples())
5707 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 !";
5708 throw INTERP_KERNEL::Exception(oss.str().c_str());
5710 MCAuto<DataArrayInt> p1(ids1->deepCopy());
5711 MCAuto<DataArrayInt> p2(ids2->deepCopy());
5712 p1->sort(true); p2->sort(true);
5713 if(!p1->isEqualWithoutConsideringStr(*p2))
5714 throw INTERP_KERNEL::Exception("DataArrayInt::FindPermutationFromFirstToSecond : the two arrays are not lying on same ids ! Impossible to find a permutation between the 2 arrays !");
5715 p1=ids1->checkAndPreparePermutation();
5716 p2=ids2->checkAndPreparePermutation();
5717 p2=p2->invertArrayO2N2N2O(p2->getNumberOfTuples());
5718 p2=p2->selectByTupleIdSafe(p1->begin(),p1->end());
5723 * Returns two arrays describing a surjective mapping from \a this set of values (\a A)
5724 * onto a set of values of size \a targetNb (\a B). The surjective function is
5725 * \a B[ \a A[ i ]] = i. That is to say that for each \a id in [0,\a targetNb), where \a
5726 * targetNb < \a this->getNumberOfTuples(), there exists at least one tupleId (\a tid) so
5727 * that <em> this->getIJ( tid, 0 ) == id</em>. <br>
5728 * The first of out arrays returns indices of elements of \a this array, grouped by their
5729 * place in the set \a B. The second out array is the index of the first one; it shows how
5730 * many elements of \a A are mapped into each element of \a B. <br>
5732 * mapping and its usage in renumbering see \ref numbering. <br>
5734 * - \a this: [0,3,2,3,2,2,1,2]
5736 * - \a arr: [0, 6, 2,4,5,7, 1,3]
5737 * - \a arrI: [0,1,2,6,8]
5739 * This result means: <br>
5740 * the element of \a B 0 encounters within \a A once (\a arrI[ 0+1 ] - \a arrI[ 0 ]) and
5741 * its index within \a A is 0 ( \a arr[ 0:1 ] == \a arr[ \a arrI[ 0 ] : \a arrI[ 0+1 ]]);<br>
5742 * the element of \a B 2 encounters within \a A 4 times (\a arrI[ 2+1 ] - \a arrI[ 2 ]) and
5743 * its indices within \a A are [2,4,5,7] ( \a arr[ 2:6 ] == \a arr[ \a arrI[ 2 ] :
5744 * \a arrI[ 2+1 ]]); <br> etc.
5745 * \param [in] targetNb - the size of the set \a B. \a targetNb must be equal or more
5746 * than the maximal value of \a A.
5747 * \param [out] arr - a new instance of DataArrayInt returning indices of
5748 * elements of \a this, grouped by their place in the set \a B. The caller is to delete
5749 * this array using decrRef() as it is no more needed.
5750 * \param [out] arrI - a new instance of DataArrayInt returning size of groups of equal
5751 * elements of \a this. The caller is to delete this array using decrRef() as it
5752 * is no more needed.
5753 * \throw If \a this is not allocated.
5754 * \throw If \a this->getNumberOfComponents() != 1.
5755 * \throw If any value in \a this is more or equal to \a targetNb.
5757 void DataArrayInt::changeSurjectiveFormat(int targetNb, DataArrayInt *&arr, DataArrayInt *&arrI) const
5760 if(getNumberOfComponents()!=1)
5761 throw INTERP_KERNEL::Exception("DataArrayInt::changeSurjectiveFormat : number of components must == 1 !");
5762 int nbOfTuples=getNumberOfTuples();
5763 MCAuto<DataArrayInt> ret(DataArrayInt::New());
5764 MCAuto<DataArrayInt> retI(DataArrayInt::New());
5765 retI->alloc(targetNb+1,1);
5766 const int *input=getConstPointer();
5767 std::vector< std::vector<int> > tmp(targetNb);
5768 for(int i=0;i<nbOfTuples;i++)
5771 if(tmp2>=0 && tmp2<targetNb)
5772 tmp[tmp2].push_back(i);
5775 std::ostringstream oss; oss << "DataArrayInt::changeSurjectiveFormat : At pos " << i << " presence of element " << tmp2 << " ! should be in [0," << targetNb << ") !";
5776 throw INTERP_KERNEL::Exception(oss.str().c_str());
5779 int *retIPtr=retI->getPointer();
5781 for(std::vector< std::vector<int> >::const_iterator it1=tmp.begin();it1!=tmp.end();it1++,retIPtr++)
5782 retIPtr[1]=retIPtr[0]+(int)((*it1).size());
5783 if(nbOfTuples!=retI->getIJ(targetNb,0))
5784 throw INTERP_KERNEL::Exception("DataArrayInt::changeSurjectiveFormat : big problem should never happen !");
5785 ret->alloc(nbOfTuples,1);
5786 int *retPtr=ret->getPointer();
5787 for(std::vector< std::vector<int> >::const_iterator it1=tmp.begin();it1!=tmp.end();it1++)
5788 retPtr=std::copy((*it1).begin(),(*it1).end(),retPtr);
5795 * Returns a new DataArrayInt containing a renumbering map in "Old to New" mode computed
5796 * from a zip representation of a surjective format (returned e.g. by
5797 * \ref MEDCoupling::DataArrayDouble::findCommonTuples() "DataArrayDouble::findCommonTuples()"
5798 * for example). The result array minimizes the permutation. <br>
5799 * For more info on renumbering see \ref numbering. <br>
5801 * - \a nbOfOldTuples: 10
5802 * - \a arr : [0,3, 5,7,9]
5803 * - \a arrIBg : [0,2,5]
5804 * - \a newNbOfTuples: 7
5805 * - result array : [0,1,2,0,3,4,5,4,6,4]
5807 * \param [in] nbOfOldTuples - number of tuples in the initial array \a arr.
5808 * \param [in] arr - the array of tuple indices grouped by \a arrIBg array.
5809 * \param [in] arrIBg - the array dividing all indices stored in \a arr into groups of
5810 * (indices of) equal values. Its every element (except the last one) points to
5811 * the first element of a group of equal values.
5812 * \param [in] arrIEnd - specifies the end of \a arrIBg, so that the last element of \a
5813 * arrIBg is \a arrIEnd[ -1 ].
5814 * \param [out] newNbOfTuples - number of tuples after surjection application.
5815 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5816 * array using decrRef() as it is no more needed.
5817 * \throw If any value of \a arr breaks condition ( 0 <= \a arr[ i ] < \a nbOfOldTuples ).
5819 DataArrayInt *DataArrayInt::ConvertIndexArrayToO2N(int nbOfOldTuples, const int *arr, const int *arrIBg, const int *arrIEnd, int &newNbOfTuples)
5821 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5822 ret->alloc(nbOfOldTuples,1);
5823 int *pt=ret->getPointer();
5824 std::fill(pt,pt+nbOfOldTuples,-1);
5825 int nbOfGrps=((int)std::distance(arrIBg,arrIEnd))-1;
5826 const int *cIPtr=arrIBg;
5827 for(int i=0;i<nbOfGrps;i++)
5828 pt[arr[cIPtr[i]]]=-(i+2);
5830 for(int iNode=0;iNode<nbOfOldTuples;iNode++)
5838 int grpId=-(pt[iNode]+2);
5839 for(int j=cIPtr[grpId];j<cIPtr[grpId+1];j++)
5841 if(arr[j]>=0 && arr[j]<nbOfOldTuples)
5845 std::ostringstream oss; oss << "DataArrayInt::ConvertIndexArrayToO2N : With element #" << j << " value is " << arr[j] << " should be in [0," << nbOfOldTuples << ") !";
5846 throw INTERP_KERNEL::Exception(oss.str().c_str());
5853 newNbOfTuples=newNb;
5858 * Returns a new DataArrayInt containing a renumbering map in "New to Old" mode,
5859 * which if applied to \a this array would make it sorted ascendingly.
5860 * For more info on renumbering see \ref numbering. <br>
5862 * - \a this: [2,0,1,1,0,1,2,0,1,1,0,0]
5863 * - result: [10,0,5,6,1,7,11,2,8,9,3,4]
5864 * - after applying result to \a this: [0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2]
5866 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
5867 * array using decrRef() as it is no more needed.
5868 * \throw If \a this is not allocated.
5869 * \throw If \a this->getNumberOfComponents() != 1.
5871 DataArrayInt *DataArrayInt::buildPermArrPerLevel() const
5874 if(getNumberOfComponents()!=1)
5875 throw INTERP_KERNEL::Exception("DataArrayInt::buildPermArrPerLevel : number of components must == 1 !");
5876 int nbOfTuples=getNumberOfTuples();
5877 const int *pt=getConstPointer();
5878 std::map<int,int> m;
5879 MCAuto<DataArrayInt> ret=DataArrayInt::New();
5880 ret->alloc(nbOfTuples,1);
5881 int *opt=ret->getPointer();
5882 for(int i=0;i<nbOfTuples;i++,pt++,opt++)
5885 std::map<int,int>::iterator it=m.find(val);
5894 m.insert(std::pair<int,int>(val,1));
5898 for(std::map<int,int>::iterator it=m.begin();it!=m.end();it++)
5900 int vt=(*it).second;
5904 pt=getConstPointer();
5905 opt=ret->getPointer();
5906 for(int i=0;i<nbOfTuples;i++,pt++,opt++)
5913 * Checks if \a this array has the given size, and if its contents is equal to an array filled with
5914 * iota(). This method is particularly useful for DataArrayInt instances that represent
5915 * a renumbering array, to check if there is a real need in renumbering.
5916 * This method checks than \a this can be considered as an identity mapping
5917 * of a set having \a sizeExpected elements into itself.
5919 * \param [in] sizeExpected - The number of elements expected.
5920 * \return bool - \a true if \a this array contents == \a range( \a this->getNumberOfTuples())
5921 * \throw If \a this is not allocated.
5922 * \throw If \a this->getNumberOfComponents() != 1.
5924 bool DataArrayInt::isIota(int sizeExpected) const
5927 if(getNumberOfComponents()!=1)
5929 int nbOfTuples(getNumberOfTuples());
5930 if(nbOfTuples!=sizeExpected)
5932 const int *pt=getConstPointer();
5933 for(int i=0;i<nbOfTuples;i++,pt++)
5940 * Checks if all values in \a this array are equal to \a val.
5941 * \param [in] val - value to check equality of array values to.
5942 * \return bool - \a true if all values are \a val.
5943 * \throw If \a this is not allocated.
5944 * \throw If \a this->getNumberOfComponents() != 1
5946 bool DataArrayInt::isUniform(int val) const
5949 if(getNumberOfComponents()!=1)
5950 throw INTERP_KERNEL::Exception("DataArrayInt::isUniform : must be applied on DataArrayInt with only one component, you can call 'rearrange' method before !");
5951 int nbOfTuples=getNumberOfTuples();
5952 const int *w=getConstPointer();
5953 const int *end2=w+nbOfTuples;
5961 * Checks if all values in \a this array are unique.
5962 * \return bool - \a true if condition above is true
5963 * \throw If \a this is not allocated.
5964 * \throw If \a this->getNumberOfComponents() != 1
5966 bool DataArrayInt::hasUniqueValues() const
5969 if(getNumberOfComponents()!=1)
5970 throw INTERP_KERNEL::Exception("DataArrayInt::hasOnlyUniqueValues: must be applied on DataArrayInt with only one component, you can call 'rearrange' method before !");
5971 int nbOfTuples(getNumberOfTuples());
5972 std::set<int> s(begin(),end()); // in C++11, should use unordered_set (O(1) complexity)
5973 if (s.size() != nbOfTuples)
5979 * Appends components of another array to components of \a this one, tuple by tuple.
5980 * So that the number of tuples of \a this array remains the same and the number of
5981 * components increases.
5982 * \param [in] other - the DataArrayInt to append to \a this one.
5983 * \throw If \a this is not allocated.
5984 * \throw If \a this and \a other arrays have different number of tuples.
5986 * \if ENABLE_EXAMPLES
5987 * \ref cpp_mcdataarrayint_meldwith "Here is a C++ example".
5989 * \ref py_mcdataarrayint_meldwith "Here is a Python example".
5992 void DataArrayInt::meldWith(const DataArrayInt *other)
5995 throw INTERP_KERNEL::Exception("DataArrayInt::meldWith : DataArrayInt pointer in input is NULL !");
5997 other->checkAllocated();
5998 int nbOfTuples=getNumberOfTuples();
5999 if(nbOfTuples!=other->getNumberOfTuples())
6000 throw INTERP_KERNEL::Exception("DataArrayInt::meldWith : mismatch of number of tuples !");
6001 int nbOfComp1=getNumberOfComponents();
6002 int nbOfComp2=other->getNumberOfComponents();
6003 int *newArr=(int *)malloc(nbOfTuples*(nbOfComp1+nbOfComp2)*sizeof(int));
6005 const int *inp1=getConstPointer();
6006 const int *inp2=other->getConstPointer();
6007 for(int i=0;i<nbOfTuples;i++,inp1+=nbOfComp1,inp2+=nbOfComp2)
6009 w=std::copy(inp1,inp1+nbOfComp1,w);
6010 w=std::copy(inp2,inp2+nbOfComp2,w);
6012 useArray(newArr,true,C_DEALLOC,nbOfTuples,nbOfComp1+nbOfComp2);
6013 std::vector<int> compIds(nbOfComp2);
6014 for(int i=0;i<nbOfComp2;i++)
6015 compIds[i]=nbOfComp1+i;
6016 copyPartOfStringInfoFrom2(compIds,*other);
6020 * Copy all components in a specified order from another DataArrayInt.
6021 * The specified components become the first ones in \a this array.
6022 * Both numerical and textual data is copied. The number of tuples in \a this and
6023 * the other array can be different.
6024 * \param [in] a - the array to copy data from.
6025 * \param [in] compoIds - sequence of zero based indices of components, data of which is
6027 * \throw If \a a is NULL.
6028 * \throw If \a compoIds.size() != \a a->getNumberOfComponents().
6029 * \throw If \a compoIds[i] < 0 or \a compoIds[i] > \a this->getNumberOfComponents().
6031 * \if ENABLE_EXAMPLES
6032 * \ref py_mcdataarrayint_setselectedcomponents "Here is a Python example".
6035 void DataArrayInt::setSelectedComponents(const DataArrayInt *a, const std::vector<int>& compoIds)
6038 throw INTERP_KERNEL::Exception("DataArrayInt::setSelectedComponents : input DataArrayInt is NULL !");
6040 a->checkAllocated();
6041 copyPartOfStringInfoFrom2(compoIds,*a);
6042 std::size_t partOfCompoSz=compoIds.size();
6043 int nbOfCompo=getNumberOfComponents();
6044 int nbOfTuples=std::min(getNumberOfTuples(),a->getNumberOfTuples());
6045 const int *ac=a->getConstPointer();
6046 int *nc=getPointer();
6047 for(int i=0;i<nbOfTuples;i++)
6048 for(std::size_t j=0;j<partOfCompoSz;j++,ac++)
6049 nc[nbOfCompo*i+compoIds[j]]=*ac;
6053 * Assign pointer to one array to a pointer to another appay. Reference counter of
6054 * \a arrayToSet is incremented / decremented.
6055 * \param [in] newArray - the pointer to array to assign to \a arrayToSet.
6056 * \param [in,out] arrayToSet - the pointer to array to assign to.
6058 void DataArrayInt::SetArrayIn(DataArrayInt *newArray, DataArrayInt* &arrayToSet)
6060 if(newArray!=arrayToSet)
6063 arrayToSet->decrRef();
6064 arrayToSet=newArray;
6066 arrayToSet->incrRef();
6070 DataArrayIntIterator *DataArrayInt::iterator()
6072 return new DataArrayIntIterator(this);
6076 * Creates a new DataArrayInt containing IDs (indices) of tuples holding value equal to a
6077 * given one. The ids are sorted in the ascending order.
6078 * \param [in] val - the value to find within \a this.
6079 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6080 * array using decrRef() as it is no more needed.
6081 * \throw If \a this is not allocated.
6082 * \throw If \a this->getNumberOfComponents() != 1.
6083 * \sa DataArrayInt::findIdsEqualTuple
6085 DataArrayInt *DataArrayInt::findIdsEqual(int val) const
6088 if(getNumberOfComponents()!=1)
6089 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsEqual : the array must have only one component, you can call 'rearrange' method before !");
6090 const int *cptr(getConstPointer());
6091 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
6092 int nbOfTuples=getNumberOfTuples();
6093 for(int i=0;i<nbOfTuples;i++,cptr++)
6095 ret->pushBackSilent(i);
6100 * Creates a new DataArrayInt containing IDs (indices) of tuples holding value \b not
6101 * equal to a given one.
6102 * \param [in] val - the value to ignore within \a this.
6103 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6104 * array using decrRef() as it is no more needed.
6105 * \throw If \a this is not allocated.
6106 * \throw If \a this->getNumberOfComponents() != 1.
6108 DataArrayInt *DataArrayInt::findIdsNotEqual(int val) const
6111 if(getNumberOfComponents()!=1)
6112 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsNotEqual : the array must have only one component, you can call 'rearrange' method before !");
6113 const int *cptr(getConstPointer());
6114 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
6115 int nbOfTuples=getNumberOfTuples();
6116 for(int i=0;i<nbOfTuples;i++,cptr++)
6118 ret->pushBackSilent(i);
6123 * Creates a new DataArrayInt containing IDs (indices) of tuples holding tuple equal to those defined by [ \a tupleBg , \a tupleEnd )
6124 * This method is an extension of DataArrayInt::findIdsEqual method.
6126 * \param [in] tupleBg - the begin (included) of the input tuple to find within \a this.
6127 * \param [in] tupleEnd - the end (excluded) of the input tuple to find within \a this.
6128 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6129 * array using decrRef() as it is no more needed.
6130 * \throw If \a this is not allocated.
6131 * \throw If \a this->getNumberOfComponents() != std::distance(tupleBg,tupleEnd).
6132 * \throw If \a this->getNumberOfComponents() is equal to 0.
6133 * \sa DataArrayInt::findIdsEqual
6135 DataArrayInt *DataArrayInt::findIdsEqualTuple(const int *tupleBg, const int *tupleEnd) const
6137 std::size_t nbOfCompoExp(std::distance(tupleBg,tupleEnd));
6139 if(getNumberOfComponents()!=(int)nbOfCompoExp)
6141 std::ostringstream oss; oss << "DataArrayInt::findIdsEqualTuple : mismatch of number of components. Input tuple has " << nbOfCompoExp << " whereas this array has " << getNumberOfComponents() << " components !";
6142 throw INTERP_KERNEL::Exception(oss.str().c_str());
6145 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsEqualTuple : number of components should be > 0 !");
6146 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
6147 const int *bg(begin()),*end2(end()),*work(begin());
6150 work=std::search(work,end2,tupleBg,tupleEnd);
6153 std::size_t pos(std::distance(bg,work));
6154 if(pos%nbOfCompoExp==0)
6155 ret->pushBackSilent(pos/nbOfCompoExp);
6163 * Assigns \a newValue to all elements holding \a oldValue within \a this
6164 * one-dimensional array.
6165 * \param [in] oldValue - the value to replace.
6166 * \param [in] newValue - the value to assign.
6167 * \return int - number of replacements performed.
6168 * \throw If \a this is not allocated.
6169 * \throw If \a this->getNumberOfComponents() != 1.
6171 int DataArrayInt::changeValue(int oldValue, int newValue)
6174 if(getNumberOfComponents()!=1)
6175 throw INTERP_KERNEL::Exception("DataArrayInt::changeValue : the array must have only one component, you can call 'rearrange' method before !");
6176 if(oldValue==newValue)
6178 int *start(getPointer()),*end2(start+getNbOfElems());
6180 for(int *val=start;val!=end2;val++)
6194 * Creates a new DataArrayInt containing IDs (indices) of tuples holding value equal to
6195 * one of given values.
6196 * \param [in] valsBg - an array of values to find within \a this array.
6197 * \param [in] valsEnd - specifies the end of the array \a valsBg, so that
6198 * the last value of \a valsBg is \a valsEnd[ -1 ].
6199 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6200 * array using decrRef() as it is no more needed.
6201 * \throw If \a this->getNumberOfComponents() != 1.
6203 DataArrayInt *DataArrayInt::findIdsEqualList(const int *valsBg, const int *valsEnd) const
6205 if(getNumberOfComponents()!=1)
6206 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsEqualList : the array must have only one component, you can call 'rearrange' method before !");
6207 std::set<int> vals2(valsBg,valsEnd);
6208 const int *cptr(getConstPointer());
6209 std::vector<int> res;
6210 int nbOfTuples(getNumberOfTuples());
6211 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
6212 for(int i=0;i<nbOfTuples;i++,cptr++)
6213 if(vals2.find(*cptr)!=vals2.end())
6214 ret->pushBackSilent(i);
6219 * Creates a new DataArrayInt containing IDs (indices) of tuples holding values \b not
6220 * equal to any of given values.
6221 * \param [in] valsBg - an array of values to ignore within \a this array.
6222 * \param [in] valsEnd - specifies the end of the array \a valsBg, so that
6223 * the last value of \a valsBg is \a valsEnd[ -1 ].
6224 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
6225 * array using decrRef() as it is no more needed.
6226 * \throw If \a this->getNumberOfComponents() != 1.
6228 DataArrayInt *DataArrayInt::findIdsNotEqualList(const int *valsBg, const int *valsEnd) const
6230 if(getNumberOfComponents()!=1)
6231 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsNotEqualList : the array must have only one component, you can call 'rearrange' method before !");
6232 std::set<int> vals2(valsBg,valsEnd);
6233 const int *cptr=getConstPointer();
6234 std::vector<int> res;
6235 int nbOfTuples=getNumberOfTuples();
6236 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
6237 for(int i=0;i<nbOfTuples;i++,cptr++)
6238 if(vals2.find(*cptr)==vals2.end())
6239 ret->pushBackSilent(i);
6244 * This method is an extension of DataArrayInt::findIdFirstEqual method because this method works for DataArrayInt with
6245 * any number of components excepted 0 (an INTERP_KERNEL::Exception is thrown in this case).
6246 * This method searches in \b this is there is a tuple that matched the input parameter \b tupl.
6247 * If any the tuple id is returned. If not -1 is returned.
6249 * This method throws an INTERP_KERNEL::Exception if the number of components in \b this mismatches with the size of
6250 * the input vector. An INTERP_KERNEL::Exception is thrown too if \b this is not allocated.
6252 * \return tuple id where \b tupl is. -1 if no such tuple exists in \b this.
6253 * \sa DataArrayInt::findIdSequence, DataArrayInt::presenceOfTuple.
6255 int DataArrayInt::findIdFirstEqualTuple(const std::vector<int>& tupl) const
6258 int nbOfCompo=getNumberOfComponents();
6260 throw INTERP_KERNEL::Exception("DataArrayInt::findIdFirstEqualTuple : 0 components in 'this' !");
6261 if(nbOfCompo!=(int)tupl.size())
6263 std::ostringstream oss; oss << "DataArrayInt::findIdFirstEqualTuple : 'this' contains " << nbOfCompo << " components and searching for a tuple of length " << tupl.size() << " !";
6264 throw INTERP_KERNEL::Exception(oss.str().c_str());
6266 const int *cptr=getConstPointer();
6267 std::size_t nbOfVals=getNbOfElems();
6268 for(const int *work=cptr;work!=cptr+nbOfVals;)
6270 work=std::search(work,cptr+nbOfVals,tupl.begin(),tupl.end());
6271 if(work!=cptr+nbOfVals)
6273 if(std::distance(cptr,work)%nbOfCompo!=0)
6276 return std::distance(cptr,work)/nbOfCompo;
6283 * This method searches the sequence specified in input parameter \b vals in \b this.
6284 * This works only for DataArrayInt having number of components equal to one (if not an INTERP_KERNEL::Exception will be thrown).
6285 * This method differs from DataArrayInt::findIdFirstEqualTuple in that the position is internal raw data is not considered here contrary to DataArrayInt::findIdFirstEqualTuple.
6286 * \sa DataArrayInt::findIdFirstEqualTuple
6288 int DataArrayInt::findIdSequence(const std::vector<int>& vals) const
6291 int nbOfCompo=getNumberOfComponents();
6293 throw INTERP_KERNEL::Exception("DataArrayInt::findIdSequence : works only for DataArrayInt instance with one component !");
6294 const int *cptr=getConstPointer();
6295 std::size_t nbOfVals=getNbOfElems();
6296 const int *loc=std::search(cptr,cptr+nbOfVals,vals.begin(),vals.end());
6297 if(loc!=cptr+nbOfVals)
6298 return std::distance(cptr,loc);
6303 * This method expects to be called when number of components of this is equal to one.
6304 * This method returns the tuple id, if it exists, of the first tuple equal to \b value.
6305 * If not any tuple contains \b value -1 is returned.
6306 * \sa DataArrayInt::presenceOfValue
6308 int DataArrayInt::findIdFirstEqual(int value) const
6311 if(getNumberOfComponents()!=1)
6312 throw INTERP_KERNEL::Exception("DataArrayInt::presenceOfValue : the array must have only one component, you can call 'rearrange' method before !");
6313 const int *cptr=getConstPointer();
6314 int nbOfTuples=getNumberOfTuples();
6315 const int *ret=std::find(cptr,cptr+nbOfTuples,value);
6316 if(ret!=cptr+nbOfTuples)
6317 return std::distance(cptr,ret);
6322 * This method expects to be called when number of components of this is equal to one.
6323 * This method returns the tuple id, if it exists, of the first tuple so that the value is contained in \b vals.
6324 * If not any tuple contains one of the values contained in 'vals' -1 is returned.
6325 * \sa DataArrayInt::presenceOfValue
6327 int DataArrayInt::findIdFirstEqual(const std::vector<int>& vals) const
6330 if(getNumberOfComponents()!=1)
6331 throw INTERP_KERNEL::Exception("DataArrayInt::presenceOfValue : the array must have only one component, you can call 'rearrange' method before !");
6332 std::set<int> vals2(vals.begin(),vals.end());
6333 const int *cptr=getConstPointer();
6334 int nbOfTuples=getNumberOfTuples();
6335 for(const int *w=cptr;w!=cptr+nbOfTuples;w++)
6336 if(vals2.find(*w)!=vals2.end())
6337 return std::distance(cptr,w);
6342 * This method returns the number of values in \a this that are equals to input parameter \a value.
6343 * This method only works for single component array.
6345 * \return a value in [ 0, \c this->getNumberOfTuples() )
6347 * \throw If \a this is not allocated
6350 int DataArrayInt::count(int value) const
6354 if(getNumberOfComponents()!=1)
6355 throw INTERP_KERNEL::Exception("DataArrayInt::count : must be applied on DataArrayInt with only one component, you can call 'rearrange' method before !");
6356 const int *vals=begin();
6357 int nbOfTuples=getNumberOfTuples();
6358 for(int i=0;i<nbOfTuples;i++,vals++)
6365 * This method is an extension of DataArrayInt::presenceOfValue method because this method works for DataArrayInt with
6366 * any number of components excepted 0 (an INTERP_KERNEL::Exception is thrown in this case).
6367 * This method searches in \b this is there is a tuple that matched the input parameter \b tupl.
6368 * This method throws an INTERP_KERNEL::Exception if the number of components in \b this mismatches with the size of
6369 * the input vector. An INTERP_KERNEL::Exception is thrown too if \b this is not allocated.
6370 * \sa DataArrayInt::findIdFirstEqualTuple
6372 bool DataArrayInt::presenceOfTuple(const std::vector<int>& tupl) const
6374 return findIdFirstEqualTuple(tupl)!=-1;
6379 * Returns \a true if a given value is present within \a this one-dimensional array.
6380 * \param [in] value - the value to find within \a this array.
6381 * \return bool - \a true in case if \a value is present within \a this array.
6382 * \throw If \a this is not allocated.
6383 * \throw If \a this->getNumberOfComponents() != 1.
6384 * \sa findIdFirstEqual()
6386 bool DataArrayInt::presenceOfValue(int value) const
6388 return findIdFirstEqual(value)!=-1;
6392 * This method expects to be called when number of components of this is equal to one.
6393 * This method returns true if it exists a tuple so that the value is contained in \b vals.
6394 * If not any tuple contains one of the values contained in 'vals' false is returned.
6395 * \sa DataArrayInt::findIdFirstEqual
6397 bool DataArrayInt::presenceOfValue(const std::vector<int>& vals) const
6399 return findIdFirstEqual(vals)!=-1;
6403 * Accumulates values of each component of \a this array.
6404 * \param [out] res - an array of length \a this->getNumberOfComponents(), allocated
6405 * by the caller, that is filled by this method with sum value for each
6407 * \throw If \a this is not allocated.
6409 void DataArrayInt::accumulate(int *res) const
6412 const int *ptr=getConstPointer();
6413 int nbTuple=getNumberOfTuples();
6414 int nbComps=getNumberOfComponents();
6415 std::fill(res,res+nbComps,0);
6416 for(int i=0;i<nbTuple;i++)
6417 std::transform(ptr+i*nbComps,ptr+(i+1)*nbComps,res,res,std::plus<int>());
6420 int DataArrayInt::accumulate(int compId) const
6423 const int *ptr=getConstPointer();
6424 int nbTuple=getNumberOfTuples();
6425 int nbComps=getNumberOfComponents();
6426 if(compId<0 || compId>=nbComps)
6427 throw INTERP_KERNEL::Exception("DataArrayInt::accumulate : Invalid compId specified : No such nb of components !");
6429 for(int i=0;i<nbTuple;i++)
6430 ret+=ptr[i*nbComps+compId];
6435 * This method accumulate using addition tuples in \a this using input index array [ \a bgOfIndex, \a endOfIndex ).
6436 * The returned array will have same number of components than \a this and number of tuples equal to
6437 * \c std::distance(bgOfIndex,endOfIndex) \b minus \b one.
6439 * The input index array is expected to be ascendingly sorted in which the all referenced ids should be in [0, \c this->getNumberOfTuples).
6441 * \param [in] bgOfIndex - begin (included) of the input index array.
6442 * \param [in] endOfIndex - end (excluded) of the input index array.
6443 * \return DataArrayInt * - the new instance having the same number of components than \a this.
6445 * \throw If bgOfIndex or end is NULL.
6446 * \throw If input index array is not ascendingly sorted.
6447 * \throw If there is an id in [ \a bgOfIndex, \a endOfIndex ) not in [0, \c this->getNumberOfTuples).
6448 * \throw If std::distance(bgOfIndex,endOfIndex)==0.
6450 DataArrayInt *DataArrayInt::accumulatePerChunck(const int *bgOfIndex, const int *endOfIndex) const
6452 if(!bgOfIndex || !endOfIndex)
6453 throw INTERP_KERNEL::Exception("DataArrayInt::accumulatePerChunck : input pointer NULL !");
6455 int nbCompo=getNumberOfComponents();
6456 int nbOfTuples=getNumberOfTuples();
6457 int sz=(int)std::distance(bgOfIndex,endOfIndex);
6459 throw INTERP_KERNEL::Exception("DataArrayInt::accumulatePerChunck : invalid size of input index array !");
6461 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(sz,nbCompo);
6462 const int *w=bgOfIndex;
6463 if(*w<0 || *w>=nbOfTuples)
6464 throw INTERP_KERNEL::Exception("DataArrayInt::accumulatePerChunck : The first element of the input index not in [0,nbOfTuples) !");
6465 const int *srcPt=begin()+(*w)*nbCompo;
6466 int *tmp=ret->getPointer();
6467 for(int i=0;i<sz;i++,tmp+=nbCompo,w++)
6469 std::fill(tmp,tmp+nbCompo,0);
6472 for(int j=w[0];j<w[1];j++,srcPt+=nbCompo)
6474 if(j>=0 && j<nbOfTuples)
6475 std::transform(srcPt,srcPt+nbCompo,tmp,tmp,std::plus<int>());
6478 std::ostringstream oss; oss << "DataArrayInt::accumulatePerChunck : At rank #" << i << " the input index array points to id " << j << " should be in [0," << nbOfTuples << ") !";
6479 throw INTERP_KERNEL::Exception(oss.str().c_str());
6485 std::ostringstream oss; oss << "DataArrayInt::accumulatePerChunck : At rank #" << i << " the input index array is not in ascendingly sorted.";
6486 throw INTERP_KERNEL::Exception(oss.str().c_str());
6489 ret->copyStringInfoFrom(*this);
6494 * Returns a new DataArrayInt by concatenating two given arrays, so that (1) the number
6495 * of tuples in the result array is <em> a1->getNumberOfTuples() + a2->getNumberOfTuples() -
6496 * offsetA2</em> and (2)
6497 * the number of component in the result array is same as that of each of given arrays.
6498 * First \a offsetA2 tuples of \a a2 are skipped and thus are missing from the result array.
6499 * Info on components is copied from the first of the given arrays. Number of components
6500 * in the given arrays must be the same.
6501 * \param [in] a1 - an array to include in the result array.
6502 * \param [in] a2 - another array to include in the result array.
6503 * \param [in] offsetA2 - number of tuples of \a a2 to skip.
6504 * \return DataArrayInt * - the new instance of DataArrayInt.
6505 * The caller is to delete this result array using decrRef() as it is no more
6507 * \throw If either \a a1 or \a a2 is NULL.
6508 * \throw If \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents().
6510 DataArrayInt *DataArrayInt::Aggregate(const DataArrayInt *a1, const DataArrayInt *a2, int offsetA2)
6513 throw INTERP_KERNEL::Exception("DataArrayInt::Aggregate : input DataArrayInt instance is NULL !");
6514 int nbOfComp=a1->getNumberOfComponents();
6515 if(nbOfComp!=a2->getNumberOfComponents())
6516 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Aggregation !");
6517 int nbOfTuple1=a1->getNumberOfTuples();
6518 int nbOfTuple2=a2->getNumberOfTuples();
6519 DataArrayInt *ret=DataArrayInt::New();
6520 ret->alloc(nbOfTuple1+nbOfTuple2-offsetA2,nbOfComp);
6521 int *pt=std::copy(a1->getConstPointer(),a1->getConstPointer()+nbOfTuple1*nbOfComp,ret->getPointer());
6522 std::copy(a2->getConstPointer()+offsetA2*nbOfComp,a2->getConstPointer()+nbOfTuple2*nbOfComp,pt);
6523 ret->copyStringInfoFrom(*a1);
6528 * Returns a new DataArrayInt by concatenating all given arrays, so that (1) the number
6529 * of tuples in the result array is a sum of the number of tuples of given arrays and (2)
6530 * the number of component in the result array is same as that of each of given arrays.
6531 * Info on components is copied from the first of the given arrays. Number of components
6532 * in the given arrays must be the same.
6533 * If the number of non null of elements in \a arr is equal to one the returned object is a copy of it
6534 * not the object itself.
6535 * \param [in] arr - a sequence of arrays to include in the result array.
6536 * \return DataArrayInt * - the new instance of DataArrayInt.
6537 * The caller is to delete this result array using decrRef() as it is no more
6539 * \throw If all arrays within \a arr are NULL.
6540 * \throw If getNumberOfComponents() of arrays within \a arr.
6542 DataArrayInt *DataArrayInt::Aggregate(const std::vector<const DataArrayInt *>& arr)
6544 std::vector<const DataArrayInt *> a;
6545 for(std::vector<const DataArrayInt *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
6549 throw INTERP_KERNEL::Exception("DataArrayInt::Aggregate : input list must be NON EMPTY !");
6550 std::vector<const DataArrayInt *>::const_iterator it=a.begin();
6551 int nbOfComp=(*it)->getNumberOfComponents();
6552 int nbt=(*it++)->getNumberOfTuples();
6553 for(int i=1;it!=a.end();it++,i++)
6555 if((*it)->getNumberOfComponents()!=nbOfComp)
6556 throw INTERP_KERNEL::Exception("DataArrayInt::Aggregate : Nb of components mismatch for array aggregation !");
6557 nbt+=(*it)->getNumberOfTuples();
6559 MCAuto<DataArrayInt> ret=DataArrayInt::New();
6560 ret->alloc(nbt,nbOfComp);
6561 int *pt=ret->getPointer();
6562 for(it=a.begin();it!=a.end();it++)
6563 pt=std::copy((*it)->getConstPointer(),(*it)->getConstPointer()+(*it)->getNbOfElems(),pt);
6564 ret->copyStringInfoFrom(*(a[0]));
6569 * This method takes as input a list of DataArrayInt instances \a arrs that represent each a packed index arrays.
6570 * A packed index array is an allocated array with one component, and at least one tuple. The first element
6571 * of each array in \a arrs must be 0. Each array in \a arrs is expected to be increasingly monotonic.
6572 * 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.
6574 * \return DataArrayInt * - a new object to be managed by the caller.
6576 DataArrayInt *DataArrayInt::AggregateIndexes(const std::vector<const DataArrayInt *>& arrs)
6579 for(std::vector<const DataArrayInt *>::const_iterator it4=arrs.begin();it4!=arrs.end();it4++)
6583 (*it4)->checkAllocated();
6584 if((*it4)->getNumberOfComponents()!=1)
6586 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a DataArrayInt instance with nb of compo != 1 at pos " << std::distance(arrs.begin(),it4) << " !";
6587 throw INTERP_KERNEL::Exception(oss.str().c_str());
6589 int nbTupl=(*it4)->getNumberOfTuples();
6592 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a DataArrayInt instance with nb of tuples < 1 at pos " << std::distance(arrs.begin(),it4) << " !";
6593 throw INTERP_KERNEL::Exception(oss.str().c_str());
6595 if((*it4)->front()!=0)
6597 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a DataArrayInt instance with front value != 0 at pos " << std::distance(arrs.begin(),it4) << " !";
6598 throw INTERP_KERNEL::Exception(oss.str().c_str());
6604 std::ostringstream oss; oss << "DataArrayInt::AggregateIndexes : presence of a null instance at pos " << std::distance(arrs.begin(),it4) << " !";
6605 throw INTERP_KERNEL::Exception(oss.str().c_str());
6609 throw INTERP_KERNEL::Exception("DataArrayInt::AggregateIndexes : input list must be NON EMPTY !");
6610 MCAuto<DataArrayInt> ret=DataArrayInt::New();
6611 ret->alloc(retSz,1);
6612 int *pt=ret->getPointer(); *pt++=0;
6613 for(std::vector<const DataArrayInt *>::const_iterator it=arrs.begin();it!=arrs.end();it++)
6614 pt=std::transform((*it)->begin()+1,(*it)->end(),pt,std::bind2nd(std::plus<int>(),pt[-1]));
6615 ret->copyStringInfoFrom(*(arrs[0]));
6620 * Returns in a single walk in \a this the min value and the max value in \a this.
6621 * \a this is expected to be single component array.
6623 * \param [out] minValue - the min value in \a this.
6624 * \param [out] maxValue - the max value in \a this.
6626 * \sa getMinValueInArray, getMinValue, getMaxValueInArray, getMaxValue
6628 void DataArrayInt::getMinMaxValues(int& minValue, int& maxValue) const
6631 if(getNumberOfComponents()!=1)
6632 throw INTERP_KERNEL::Exception("DataArrayInt::getMinMaxValues : must be applied on DataArrayInt with only one component !");
6633 int nbTuples(getNumberOfTuples());
6634 const int *pt(begin());
6635 minValue=std::numeric_limits<int>::max(); maxValue=-std::numeric_limits<int>::max();
6636 for(int i=0;i<nbTuples;i++,pt++)
6646 * Converts every value of \a this array to its absolute value.
6647 * \b WARNING this method is non const. If a new DataArrayInt instance should be built containing the result of abs DataArrayInt::computeAbs
6648 * should be called instead.
6650 * \throw If \a this is not allocated.
6651 * \sa DataArrayInt::computeAbs
6653 void DataArrayInt::abs()
6656 int *ptr(getPointer());
6657 std::size_t nbOfElems(getNbOfElems());
6658 std::transform(ptr,ptr+nbOfElems,ptr,std::ptr_fun<int,int>(std::abs));
6663 * This method builds a new instance of \a this object containing the result of std::abs applied of all elements in \a this.
6664 * This method is a const method (that do not change any values in \a this) contrary to DataArrayInt::abs method.
6666 * \return DataArrayInt * - the new instance of DataArrayInt containing the
6667 * same number of tuples and component as \a this array.
6668 * The caller is to delete this result array using decrRef() as it is no more
6670 * \throw If \a this is not allocated.
6671 * \sa DataArrayInt::abs
6673 DataArrayInt *DataArrayInt::computeAbs() const
6676 DataArrayInt *newArr(DataArrayInt::New());
6677 int nbOfTuples(getNumberOfTuples());
6678 int nbOfComp(getNumberOfComponents());
6679 newArr->alloc(nbOfTuples,nbOfComp);
6680 std::transform(begin(),end(),newArr->getPointer(),std::ptr_fun<int,int>(std::abs));
6681 newArr->copyStringInfoFrom(*this);
6686 * Apply a liner function to a given component of \a this array, so that
6687 * an array element <em>(x)</em> becomes \f$ a * x + b \f$.
6688 * \param [in] a - the first coefficient of the function.
6689 * \param [in] b - the second coefficient of the function.
6690 * \param [in] compoId - the index of component to modify.
6691 * \throw If \a this is not allocated.
6693 void DataArrayInt::applyLin(int a, int b, int compoId)
6696 int *ptr=getPointer()+compoId;
6697 int nbOfComp=getNumberOfComponents();
6698 int nbOfTuple=getNumberOfTuples();
6699 for(int i=0;i<nbOfTuple;i++,ptr+=nbOfComp)
6705 * Apply a liner function to all elements of \a this array, so that
6706 * an element _x_ becomes \f$ a * x + b \f$.
6707 * \param [in] a - the first coefficient of the function.
6708 * \param [in] b - the second coefficient of the function.
6709 * \throw If \a this is not allocated.
6711 void DataArrayInt::applyLin(int a, int b)
6714 int *ptr=getPointer();
6715 std::size_t nbOfElems=getNbOfElems();
6716 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
6722 * Returns a full copy of \a this array except that sign of all elements is reversed.
6723 * \return DataArrayInt * - the new instance of DataArrayInt containing the
6724 * same number of tuples and component as \a this array.
6725 * The caller is to delete this result array using decrRef() as it is no more
6727 * \throw If \a this is not allocated.
6729 DataArrayInt *DataArrayInt::negate() const
6732 DataArrayInt *newArr=DataArrayInt::New();
6733 int nbOfTuples=getNumberOfTuples();
6734 int nbOfComp=getNumberOfComponents();
6735 newArr->alloc(nbOfTuples,nbOfComp);
6736 const int *cptr=getConstPointer();
6737 std::transform(cptr,cptr+nbOfTuples*nbOfComp,newArr->getPointer(),std::negate<int>());
6738 newArr->copyStringInfoFrom(*this);
6743 * Modify all elements of \a this array, so that
6744 * an element _x_ becomes \f$ numerator / x \f$.
6745 * \warning If an exception is thrown because of presence of 0 element in \a this
6746 * array, all elements processed before detection of the zero element remain
6748 * \param [in] numerator - the numerator used to modify array elements.
6749 * \throw If \a this is not allocated.
6750 * \throw If there is an element equal to 0 in \a this array.
6752 void DataArrayInt::applyInv(int numerator)
6755 int *ptr=getPointer();
6756 std::size_t nbOfElems=getNbOfElems();
6757 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
6761 *ptr=numerator/(*ptr);
6765 std::ostringstream oss; oss << "DataArrayInt::applyInv : presence of null value in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
6767 throw INTERP_KERNEL::Exception(oss.str().c_str());
6774 * Modify all elements of \a this array, so that
6775 * an element _x_ becomes \f$ x / val \f$.
6776 * \param [in] val - the denominator used to modify array elements.
6777 * \throw If \a this is not allocated.
6778 * \throw If \a val == 0.
6780 void DataArrayInt::applyDivideBy(int val)
6783 throw INTERP_KERNEL::Exception("DataArrayInt::applyDivideBy : Trying to divide by 0 !");
6785 int *ptr=getPointer();
6786 std::size_t nbOfElems=getNbOfElems();
6787 std::transform(ptr,ptr+nbOfElems,ptr,std::bind2nd(std::divides<int>(),val));
6792 * Modify all elements of \a this array, so that
6793 * an element _x_ becomes <em> x % val </em>.
6794 * \param [in] val - the divisor used to modify array elements.
6795 * \throw If \a this is not allocated.
6796 * \throw If \a val <= 0.
6798 void DataArrayInt::applyModulus(int val)
6801 throw INTERP_KERNEL::Exception("DataArrayInt::applyDivideBy : Trying to operate modulus on value <= 0 !");
6803 int *ptr=getPointer();
6804 std::size_t nbOfElems=getNbOfElems();
6805 std::transform(ptr,ptr+nbOfElems,ptr,std::bind2nd(std::modulus<int>(),val));
6811 GreatEqual(int v):_v(v) { }
6812 bool operator()(int v) const { return v>=_v; }
6818 GreaterThan(int v):_v(v) { }
6819 bool operator()(int v) const { return v>_v; }
6825 LowerEqual(int v):_v(v) { }
6826 bool operator()(int v) const { return v<=_v; }
6832 LowerThan(int v):_v(v) { }
6833 bool operator()(int v) const { return v<_v; }
6839 InRange(int a, int b):_a(a),_b(b) { }
6840 bool operator()(int v) const { return v>=_a && v<_b; }
6845 * This method works only on data array with one component.
6846 * This method returns a newly allocated array storing stored ascendantly tuple ids in \b this so that
6847 * this[*id] in [\b vmin,\b vmax)
6849 * \param [in] vmin begin of range. This value is included in range (included).
6850 * \param [in] vmax end of range. This value is \b not included in range (excluded).
6851 * \return a newly allocated data array that the caller should deal with.
6853 * \sa DataArrayInt::findIdsNotInRange , DataArrayInt::findIdsStricltyNegative
6855 DataArrayInt *DataArrayInt::findIdsInRange(int vmin, int vmax) const
6857 InRange ir(vmin,vmax);
6858 MCAuto<DataArrayInt> ret(findIdsAdv(ir));
6864 NotInRange(int a, int b):_a(a),_b(b) { }
6865 bool operator()(int v) const { return v<_a || v>=_b; }
6870 * This method works only on data array with one component.
6871 * This method returns a newly allocated array storing stored ascendantly tuple ids in \b this so that
6872 * this[*id] \b not in [\b vmin,\b vmax)
6874 * \param [in] vmin begin of range. This value is \b not included in range (excluded).
6875 * \param [in] vmax end of range. This value is included in range (included).
6876 * \return a newly allocated data array that the caller should deal with.
6878 * \sa DataArrayInt::findIdsInRange , DataArrayInt::findIdsStricltyNegative
6880 DataArrayInt *DataArrayInt::findIdsNotInRange(int vmin, int vmax) const
6882 NotInRange nir(vmin,vmax);
6883 MCAuto<DataArrayInt> ret(findIdsAdv(nir));
6888 * This method works only on data array with one component. This method returns a newly allocated array storing stored ascendantly of tuple ids in \a this so that this[id]<0.
6890 * \return a newly allocated data array that the caller should deal with.
6891 * \sa DataArrayInt::findIdsInRange
6893 DataArrayInt *DataArrayInt::findIdsStricltyNegative() const
6896 MCAuto<DataArrayInt> ret(findIdsAdv(lt));
6900 MCAuto<DataArrayInt> DataArrayInt::findIdsGreaterOrEqualTo(int val) const
6903 return findIdsAdv(ge);
6906 MCAuto<DataArrayInt> DataArrayInt::findIdsGreaterThan(int val) const
6908 GreaterThan gt(val);
6909 return findIdsAdv(gt);
6912 MCAuto<DataArrayInt> DataArrayInt::findIdsLowerOrEqualTo(int val) const
6915 return findIdsAdv(le);
6918 MCAuto<DataArrayInt> DataArrayInt::findIdsLowerThan(int val) const
6921 return findIdsAdv(lt);
6925 * This method works only on data array with one component.
6926 * 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.
6928 * \param [in] vmin begin of range. This value is included in range (included).
6929 * \param [in] vmax end of range. This value is \b not included in range (excluded).
6930 * \return if all ids in \a this are so that (*this)[i]==i for all i in [ 0, \c this->getNumberOfTuples() ). */
6931 bool DataArrayInt::checkAllIdsInRange(int vmin, int vmax) const
6934 if(getNumberOfComponents()!=1)
6935 throw INTERP_KERNEL::Exception("DataArrayInt::checkAllIdsInRange : this must have exactly one component !");
6936 int nbOfTuples=getNumberOfTuples();
6938 const int *cptr=getConstPointer();
6939 for(int i=0;i<nbOfTuples;i++,cptr++)
6941 if(*cptr>=vmin && *cptr<vmax)
6942 { ret=ret && *cptr==i; }
6945 std::ostringstream oss; oss << "DataArrayInt::checkAllIdsInRange : tuple #" << i << " has value " << *cptr << " should be in [" << vmin << "," << vmax << ") !";
6946 throw INTERP_KERNEL::Exception(oss.str().c_str());
6953 * Modify all elements of \a this array, so that
6954 * an element _x_ becomes <em> val % x </em>.
6955 * \warning If an exception is thrown because of presence of an element <= 0 in \a this
6956 * array, all elements processed before detection of the zero element remain
6958 * \param [in] val - the divident used to modify array elements.
6959 * \throw If \a this is not allocated.
6960 * \throw If there is an element equal to or less than 0 in \a this array.
6962 void DataArrayInt::applyRModulus(int val)
6965 int *ptr=getPointer();
6966 std::size_t nbOfElems=getNbOfElems();
6967 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
6975 std::ostringstream oss; oss << "DataArrayInt::applyRModulus : presence of value <=0 in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
6977 throw INTERP_KERNEL::Exception(oss.str().c_str());
6984 * Modify all elements of \a this array, so that
6985 * an element _x_ becomes <em> val ^ x </em>.
6986 * \param [in] val - the value used to apply pow on all array elements.
6987 * \throw If \a this is not allocated.
6988 * \throw If \a val < 0.
6990 void DataArrayInt::applyPow(int val)
6994 throw INTERP_KERNEL::Exception("DataArrayInt::applyPow : input pow in < 0 !");
6995 int *ptr=getPointer();
6996 std::size_t nbOfElems=getNbOfElems();
6999 std::fill(ptr,ptr+nbOfElems,1);
7002 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
7005 for(int j=0;j<val;j++)
7013 * Modify all elements of \a this array, so that
7014 * an element _x_ becomes \f$ val ^ x \f$.
7015 * \param [in] val - the value used to apply pow on all array elements.
7016 * \throw If \a this is not allocated.
7017 * \throw If there is an element < 0 in \a this array.
7018 * \warning If an exception is thrown because of presence of 0 element in \a this
7019 * array, all elements processed before detection of the zero element remain
7022 void DataArrayInt::applyRPow(int val)
7025 int *ptr=getPointer();
7026 std::size_t nbOfElems=getNbOfElems();
7027 for(std::size_t i=0;i<nbOfElems;i++,ptr++)
7032 for(int j=0;j<*ptr;j++)
7038 std::ostringstream oss; oss << "DataArrayInt::applyRPow : presence of negative value in tuple #" << i/getNumberOfComponents() << " component #" << i%getNumberOfComponents();
7040 throw INTERP_KERNEL::Exception(oss.str().c_str());
7047 * Returns a new DataArrayInt by aggregating two given arrays, so that (1) the number
7048 * of components in the result array is a sum of the number of components of given arrays
7049 * and (2) the number of tuples in the result array is same as that of each of given
7050 * arrays. In other words the i-th tuple of result array includes all components of
7051 * i-th tuples of all given arrays.
7052 * Number of tuples in the given arrays must be the same.
7053 * \param [in] a1 - an array to include in the result array.
7054 * \param [in] a2 - another array to include in the result array.
7055 * \return DataArrayInt * - the new instance of DataArrayInt.
7056 * The caller is to delete this result array using decrRef() as it is no more
7058 * \throw If both \a a1 and \a a2 are NULL.
7059 * \throw If any given array is not allocated.
7060 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
7062 DataArrayInt *DataArrayInt::Meld(const DataArrayInt *a1, const DataArrayInt *a2)
7064 std::vector<const DataArrayInt *> arr(2);
7065 arr[0]=a1; arr[1]=a2;
7070 * Returns a new DataArrayInt by aggregating all given arrays, so that (1) the number
7071 * of components in the result array is a sum of the number of components of given arrays
7072 * and (2) the number of tuples in the result array is same as that of each of given
7073 * arrays. In other words the i-th tuple of result array includes all components of
7074 * i-th tuples of all given arrays.
7075 * Number of tuples in the given arrays must be the same.
7076 * \param [in] arr - a sequence of arrays to include in the result array.
7077 * \return DataArrayInt * - the new instance of DataArrayInt.
7078 * The caller is to delete this result array using decrRef() as it is no more
7080 * \throw If all arrays within \a arr are NULL.
7081 * \throw If any given array is not allocated.
7082 * \throw If getNumberOfTuples() of arrays within \a arr is different.
7084 DataArrayInt *DataArrayInt::Meld(const std::vector<const DataArrayInt *>& arr)
7086 std::vector<const DataArrayInt *> a;
7087 for(std::vector<const DataArrayInt *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
7091 throw INTERP_KERNEL::Exception("DataArrayInt::Meld : array must be NON empty !");
7092 std::vector<const DataArrayInt *>::const_iterator it;
7093 for(it=a.begin();it!=a.end();it++)
7094 (*it)->checkAllocated();
7096 int nbOfTuples=(*it)->getNumberOfTuples();
7097 std::vector<int> nbc(a.size());
7098 std::vector<const int *> pts(a.size());
7099 nbc[0]=(*it)->getNumberOfComponents();
7100 pts[0]=(*it++)->getConstPointer();
7101 for(int i=1;it!=a.end();it++,i++)
7103 if(nbOfTuples!=(*it)->getNumberOfTuples())
7104 throw INTERP_KERNEL::Exception("DataArrayInt::meld : mismatch of number of tuples !");
7105 nbc[i]=(*it)->getNumberOfComponents();
7106 pts[i]=(*it)->getConstPointer();
7108 int totalNbOfComp=std::accumulate(nbc.begin(),nbc.end(),0);
7109 DataArrayInt *ret=DataArrayInt::New();
7110 ret->alloc(nbOfTuples,totalNbOfComp);
7111 int *retPtr=ret->getPointer();
7112 for(int i=0;i<nbOfTuples;i++)
7113 for(int j=0;j<(int)a.size();j++)
7115 retPtr=std::copy(pts[j],pts[j]+nbc[j],retPtr);
7119 for(int i=0;i<(int)a.size();i++)
7120 for(int j=0;j<nbc[i];j++,k++)
7121 ret->setInfoOnComponent(k,a[i]->getInfoOnComponent(j));
7126 * Returns a new DataArrayInt which is a minimal partition of elements of \a groups.
7127 * The i-th item of the result array is an ID of a set of elements belonging to a
7128 * unique set of groups, which the i-th element is a part of. This set of elements
7129 * belonging to a unique set of groups is called \a family, so the result array contains
7130 * IDs of families each element belongs to.
7132 * \b Example: if we have two groups of elements: \a group1 [0,4] and \a group2 [ 0,1,2 ],
7133 * then there are 3 families:
7134 * - \a family1 (with ID 1) contains element [0] belonging to ( \a group1 + \a group2 ),
7135 * - \a family2 (with ID 2) contains elements [4] belonging to ( \a group1 ),
7136 * - \a family3 (with ID 3) contains element [1,2] belonging to ( \a group2 ), <br>
7137 * and the result array contains IDs of families [ 1,3,3,0,2 ]. <br> Note a family ID 0 which
7138 * stands for the element #3 which is in none of groups.
7140 * \param [in] groups - sequence of groups of element IDs.
7141 * \param [in] newNb - total number of elements; it must be more than max ID of element
7143 * \param [out] fidsOfGroups - IDs of families the elements of each group belong to.
7144 * \return DataArrayInt * - a new instance of DataArrayInt containing IDs of families
7145 * each element with ID from range [0, \a newNb ) belongs to. The caller is to
7146 * delete this array using decrRef() as it is no more needed.
7147 * \throw If any element ID in \a groups violates condition ( 0 <= ID < \a newNb ).
7149 DataArrayInt *DataArrayInt::MakePartition(const std::vector<const DataArrayInt *>& groups, int newNb, std::vector< std::vector<int> >& fidsOfGroups)
7151 std::vector<const DataArrayInt *> groups2;
7152 for(std::vector<const DataArrayInt *>::const_iterator it4=groups.begin();it4!=groups.end();it4++)
7154 groups2.push_back(*it4);
7155 MCAuto<DataArrayInt> ret=DataArrayInt::New();
7156 ret->alloc(newNb,1);
7157 int *retPtr=ret->getPointer();
7158 std::fill(retPtr,retPtr+newNb,0);
7160 for(std::vector<const DataArrayInt *>::const_iterator iter=groups2.begin();iter!=groups2.end();iter++)
7162 const int *ptr=(*iter)->getConstPointer();
7163 std::size_t nbOfElem=(*iter)->getNbOfElems();
7165 for(int j=0;j<sfid;j++)
7168 for(std::size_t i=0;i<nbOfElem;i++)
7170 if(ptr[i]>=0 && ptr[i]<newNb)
7172 if(retPtr[ptr[i]]==j)
7180 std::ostringstream oss; oss << "DataArrayInt::MakePartition : In group \"" << (*iter)->getName() << "\" in tuple #" << i << " value = " << ptr[i] << " ! Should be in [0," << newNb;
7182 throw INTERP_KERNEL::Exception(oss.str().c_str());
7189 fidsOfGroups.clear();
7190 fidsOfGroups.resize(groups2.size());
7192 for(std::vector<const DataArrayInt *>::const_iterator iter=groups2.begin();iter!=groups2.end();iter++,grId++)
7195 const int *ptr=(*iter)->getConstPointer();
7196 std::size_t nbOfElem=(*iter)->getNbOfElems();
7197 for(const int *p=ptr;p!=ptr+nbOfElem;p++)
7198 tmp.insert(retPtr[*p]);
7199 fidsOfGroups[grId].insert(fidsOfGroups[grId].end(),tmp.begin(),tmp.end());
7205 * Returns a new DataArrayInt which contains all elements of given one-dimensional
7206 * arrays. The result array does not contain any duplicates and its values
7207 * are sorted in ascending order.
7208 * \param [in] arr - sequence of DataArrayInt's to unite.
7209 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
7210 * array using decrRef() as it is no more needed.
7211 * \throw If any \a arr[i] is not allocated.
7212 * \throw If \a arr[i]->getNumberOfComponents() != 1.
7214 DataArrayInt *DataArrayInt::BuildUnion(const std::vector<const DataArrayInt *>& arr)
7216 std::vector<const DataArrayInt *> a;
7217 for(std::vector<const DataArrayInt *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
7220 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
7222 (*it)->checkAllocated();
7223 if((*it)->getNumberOfComponents()!=1)
7224 throw INTERP_KERNEL::Exception("DataArrayInt::BuildUnion : only single component allowed !");
7228 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
7230 const int *pt=(*it)->getConstPointer();
7231 int nbOfTuples=(*it)->getNumberOfTuples();
7232 r.insert(pt,pt+nbOfTuples);
7234 DataArrayInt *ret=DataArrayInt::New();
7235 ret->alloc((int)r.size(),1);
7236 std::copy(r.begin(),r.end(),ret->getPointer());
7241 * Returns a new DataArrayInt which contains elements present in each of given one-dimensional
7242 * arrays. The result array does not contain any duplicates and its values
7243 * are sorted in ascending order.
7244 * \param [in] arr - sequence of DataArrayInt's to intersect.
7245 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
7246 * array using decrRef() as it is no more needed.
7247 * \throw If any \a arr[i] is not allocated.
7248 * \throw If \a arr[i]->getNumberOfComponents() != 1.
7250 DataArrayInt *DataArrayInt::BuildIntersection(const std::vector<const DataArrayInt *>& arr)
7252 std::vector<const DataArrayInt *> a;
7253 for(std::vector<const DataArrayInt *>::const_iterator it4=arr.begin();it4!=arr.end();it4++)
7256 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
7258 (*it)->checkAllocated();
7259 if((*it)->getNumberOfComponents()!=1)
7260 throw INTERP_KERNEL::Exception("DataArrayInt::BuildIntersection : only single component allowed !");
7264 for(std::vector<const DataArrayInt *>::const_iterator it=a.begin();it!=a.end();it++)
7266 const int *pt=(*it)->getConstPointer();
7267 int nbOfTuples=(*it)->getNumberOfTuples();
7268 std::set<int> s1(pt,pt+nbOfTuples);
7272 std::set_intersection(r.begin(),r.end(),s1.begin(),s1.end(),inserter(r2,r2.end()));
7278 DataArrayInt *ret(DataArrayInt::New());
7279 ret->alloc((int)r.size(),1);
7280 std::copy(r.begin(),r.end(),ret->getPointer());
7285 namespace MEDCouplingImpl
7290 OpSwitchedOn(int *pt):_pt(pt),_cnt(0) { }
7291 void operator()(const bool& b) { if(b) *_pt++=_cnt; _cnt++; }
7300 OpSwitchedOff(int *pt):_pt(pt),_cnt(0) { }
7301 void operator()(const bool& b) { if(!b) *_pt++=_cnt; _cnt++; }
7310 * This method returns the list of ids in ascending mode so that v[id]==true.
7312 DataArrayInt *DataArrayInt::BuildListOfSwitchedOn(const std::vector<bool>& v)
7314 int sz((int)std::count(v.begin(),v.end(),true));
7315 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(sz,1);
7316 std::for_each(v.begin(),v.end(),MEDCouplingImpl::OpSwitchedOn(ret->getPointer()));
7321 * This method returns the list of ids in ascending mode so that v[id]==false.
7323 DataArrayInt *DataArrayInt::BuildListOfSwitchedOff(const std::vector<bool>& v)
7325 int sz((int)std::count(v.begin(),v.end(),false));
7326 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(sz,1);
7327 std::for_each(v.begin(),v.end(),MEDCouplingImpl::OpSwitchedOff(ret->getPointer()));
7332 * This method allows to put a vector of vector of integer into a more compact data stucture (skyline).
7333 * This method is not available into python because no available optimized data structure available to map std::vector< std::vector<int> >.
7335 * \param [in] v the input data structure to be translate into skyline format.
7336 * \param [out] data the first element of the skyline format. The user is expected to deal with newly allocated array.
7337 * \param [out] dataIndex the second element of the skyline format.
7339 void DataArrayInt::PutIntoToSkylineFrmt(const std::vector< std::vector<int> >& v, DataArrayInt *& data, DataArrayInt *& dataIndex)
7341 int sz((int)v.size());
7342 MCAuto<DataArrayInt> ret0(DataArrayInt::New()),ret1(DataArrayInt::New());
7343 ret1->alloc(sz+1,1);
7344 int *pt(ret1->getPointer()); *pt=0;
7345 for(int i=0;i<sz;i++,pt++)
7346 pt[1]=pt[0]+(int)v[i].size();
7347 ret0->alloc(ret1->back(),1);
7348 pt=ret0->getPointer();
7349 for(int i=0;i<sz;i++)
7350 pt=std::copy(v[i].begin(),v[i].end(),pt);
7351 data=ret0.retn(); dataIndex=ret1.retn();
7355 * Returns a new DataArrayInt which contains a complement of elements of \a this
7356 * one-dimensional array. I.e. the result array contains all elements from the range [0,
7357 * \a nbOfElement) not present in \a this array.
7358 * \param [in] nbOfElement - maximal size of the result array.
7359 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
7360 * array using decrRef() as it is no more needed.
7361 * \throw If \a this is not allocated.
7362 * \throw If \a this->getNumberOfComponents() != 1.
7363 * \throw If any element \a x of \a this array violates condition ( 0 <= \a x < \a
7366 DataArrayInt *DataArrayInt::buildComplement(int nbOfElement) const
7369 if(getNumberOfComponents()!=1)
7370 throw INTERP_KERNEL::Exception("DataArrayInt::buildComplement : only single component allowed !");
7371 std::vector<bool> tmp(nbOfElement);
7372 const int *pt=getConstPointer();
7373 int nbOfTuples=getNumberOfTuples();
7374 for(const int *w=pt;w!=pt+nbOfTuples;w++)
7375 if(*w>=0 && *w<nbOfElement)
7378 throw INTERP_KERNEL::Exception("DataArrayInt::buildComplement : an element is not in valid range : [0,nbOfElement) !");
7379 int nbOfRetVal=(int)std::count(tmp.begin(),tmp.end(),false);
7380 DataArrayInt *ret=DataArrayInt::New();
7381 ret->alloc(nbOfRetVal,1);
7383 int *retPtr=ret->getPointer();
7384 for(int i=0;i<nbOfElement;i++)
7391 * Returns a new DataArrayInt containing elements of \a this one-dimensional missing
7392 * from an \a other one-dimensional array.
7393 * \param [in] other - a DataArrayInt containing elements not to include in the result array.
7394 * \return DataArrayInt * - a new instance of DataArrayInt with one component. The
7395 * caller is to delete this array using decrRef() as it is no more needed.
7396 * \throw If \a other is NULL.
7397 * \throw If \a other is not allocated.
7398 * \throw If \a other->getNumberOfComponents() != 1.
7399 * \throw If \a this is not allocated.
7400 * \throw If \a this->getNumberOfComponents() != 1.
7401 * \sa DataArrayInt::buildSubstractionOptimized()
7403 DataArrayInt *DataArrayInt::buildSubstraction(const DataArrayInt *other) const
7406 throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstraction : DataArrayInt pointer in input is NULL !");
7408 other->checkAllocated();
7409 if(getNumberOfComponents()!=1)
7410 throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstraction : only single component allowed !");
7411 if(other->getNumberOfComponents()!=1)
7412 throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstraction : only single component allowed for other type !");
7413 const int *pt=getConstPointer();
7414 int nbOfTuples=getNumberOfTuples();
7415 std::set<int> s1(pt,pt+nbOfTuples);
7416 pt=other->getConstPointer();
7417 nbOfTuples=other->getNumberOfTuples();
7418 std::set<int> s2(pt,pt+nbOfTuples);
7420 std::set_difference(s1.begin(),s1.end(),s2.begin(),s2.end(),std::back_insert_iterator< std::vector<int> >(r));
7421 DataArrayInt *ret=DataArrayInt::New();
7422 ret->alloc((int)r.size(),1);
7423 std::copy(r.begin(),r.end(),ret->getPointer());
7428 * \a this is expected to have one component and to be sorted ascendingly (as for \a other).
7429 * \a other is expected to be a part of \a this. If not DataArrayInt::buildSubstraction should be called instead.
7431 * \param [in] other an array with one component and expected to be sorted ascendingly.
7432 * \ret list of ids in \a this but not in \a other.
7433 * \sa DataArrayInt::buildSubstraction
7435 DataArrayInt *DataArrayInt::buildSubstractionOptimized(const DataArrayInt *other) const
7437 static const char *MSG="DataArrayInt::buildSubstractionOptimized : only single component allowed !";
7438 if(!other) throw INTERP_KERNEL::Exception("DataArrayInt::buildSubstractionOptimized : NULL input array !");
7439 checkAllocated(); other->checkAllocated();
7440 if(getNumberOfComponents()!=1) throw INTERP_KERNEL::Exception(MSG);
7441 if(other->getNumberOfComponents()!=1) throw INTERP_KERNEL::Exception(MSG);
7442 const int *pt1Bg(begin()),*pt1End(end()),*pt2Bg(other->begin()),*pt2End(other->end());
7443 const int *work1(pt1Bg),*work2(pt2Bg);
7444 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
7445 for(;work1!=pt1End;work1++)
7447 if(work2!=pt2End && *work1==*work2)
7450 ret->pushBackSilent(*work1);
7457 * Returns a new DataArrayInt which contains all elements of \a this and a given
7458 * one-dimensional arrays. The result array does not contain any duplicates
7459 * and its values are sorted in ascending order.
7460 * \param [in] other - an array to unite with \a this one.
7461 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
7462 * array using decrRef() as it is no more needed.
7463 * \throw If \a this or \a other is not allocated.
7464 * \throw If \a this->getNumberOfComponents() != 1.
7465 * \throw If \a other->getNumberOfComponents() != 1.
7467 DataArrayInt *DataArrayInt::buildUnion(const DataArrayInt *other) const
7469 std::vector<const DataArrayInt *>arrs(2);
7470 arrs[0]=this; arrs[1]=other;
7471 return BuildUnion(arrs);
7476 * Returns a new DataArrayInt which contains elements present in both \a this and a given
7477 * one-dimensional arrays. The result array does not contain any duplicates
7478 * and its values are sorted in ascending order.
7479 * \param [in] other - an array to intersect with \a this one.
7480 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
7481 * array using decrRef() as it is no more needed.
7482 * \throw If \a this or \a other is not allocated.
7483 * \throw If \a this->getNumberOfComponents() != 1.
7484 * \throw If \a other->getNumberOfComponents() != 1.
7486 DataArrayInt *DataArrayInt::buildIntersection(const DataArrayInt *other) const
7488 std::vector<const DataArrayInt *>arrs(2);
7489 arrs[0]=this; arrs[1]=other;
7490 return BuildIntersection(arrs);
7494 * This method can be applied on allocated with one component DataArrayInt instance.
7495 * This method is typically relevant for sorted arrays. All consecutive duplicated items in \a this will appear only once in returned DataArrayInt instance.
7496 * 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]
7498 * \return a newly allocated array that contain the result of the unique operation applied on \a this.
7499 * \throw if \a this is not allocated or if \a this has not exactly one component.
7500 * \sa DataArrayInt::buildUniqueNotSorted
7502 DataArrayInt *DataArrayInt::buildUnique() const
7505 if(getNumberOfComponents()!=1)
7506 throw INTERP_KERNEL::Exception("DataArrayInt::buildUnique : only single component allowed !");
7507 int nbOfTuples=getNumberOfTuples();
7508 MCAuto<DataArrayInt> tmp=deepCopy();
7509 int *data=tmp->getPointer();
7510 int *last=std::unique(data,data+nbOfTuples);
7511 MCAuto<DataArrayInt> ret=DataArrayInt::New();
7512 ret->alloc(std::distance(data,last),1);
7513 std::copy(data,last,ret->getPointer());
7518 * This method can be applied on allocated with one component DataArrayInt instance.
7519 * This method keep elements only once by keeping the same order in \a this that is not expected to be sorted.
7521 * \return a newly allocated array that contain the result of the unique operation applied on \a this.
7523 * \throw if \a this is not allocated or if \a this has not exactly one component.
7525 * \sa DataArrayInt::buildUnique
7527 DataArrayInt *DataArrayInt::buildUniqueNotSorted() const
7530 if(getNumberOfComponents()!=1)
7531 throw INTERP_KERNEL::Exception("DataArrayInt::buildUniqueNotSorted : only single component allowed !");
7533 getMinMaxValues(minVal,maxVal);
7534 std::vector<bool> b(maxVal-minVal+1,false);
7535 const int *ptBg(begin()),*endBg(end());
7536 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(0,1);
7537 for(const int *pt=ptBg;pt!=endBg;pt++)
7541 ret->pushBackSilent(*pt);
7545 ret->copyStringInfoFrom(*this);
7550 * Returns a new DataArrayInt which contains size of every of groups described by \a this
7551 * "index" array. Such "index" array is returned for example by
7552 * \ref MEDCoupling::MEDCouplingUMesh::buildDescendingConnectivity
7553 * "MEDCouplingUMesh::buildDescendingConnectivity" and
7554 * \ref MEDCoupling::MEDCouplingUMesh::getNodalConnectivityIndex
7555 * "MEDCouplingUMesh::getNodalConnectivityIndex" etc.
7556 * This method preforms the reverse operation of DataArrayInt::computeOffsetsFull.
7557 * \return DataArrayInt * - a new instance of DataArrayInt, whose number of tuples
7558 * equals to \a this->getNumberOfComponents() - 1, and number of components is 1.
7559 * The caller is to delete this array using decrRef() as it is no more needed.
7560 * \throw If \a this is not allocated.
7561 * \throw If \a this->getNumberOfComponents() != 1.
7562 * \throw If \a this->getNumberOfTuples() < 2.
7565 * - this contains [1,3,6,7,7,9,15]
7566 * - result array contains [2,3,1,0,2,6],
7567 * where 2 = 3 - 1, 3 = 6 - 3, 1 = 7 - 6 etc.
7569 * \sa DataArrayInt::computeOffsetsFull
7571 DataArrayInt *DataArrayInt::deltaShiftIndex() const
7574 if(getNumberOfComponents()!=1)
7575 throw INTERP_KERNEL::Exception("DataArrayInt::deltaShiftIndex : only single component allowed !");
7576 int nbOfTuples=getNumberOfTuples();
7578 throw INTERP_KERNEL::Exception("DataArrayInt::deltaShiftIndex : 1 tuple at least must be present in 'this' !");
7579 const int *ptr=getConstPointer();
7580 DataArrayInt *ret=DataArrayInt::New();
7581 ret->alloc(nbOfTuples-1,1);
7582 int *out=ret->getPointer();
7583 std::transform(ptr+1,ptr+nbOfTuples,ptr,out,std::minus<int>());
7588 * Modifies \a this one-dimensional array so that value of each element \a x
7589 * of \a this array (\a a) is computed as \f$ x_i = \sum_{j=0}^{i-1} a[ j ] \f$.
7590 * Or: for each i>0 new[i]=new[i-1]+old[i-1] for i==0 new[i]=0. Number of tuples
7591 * and components remains the same.<br>
7592 * This method is useful for allToAllV in MPI with contiguous policy. This method
7593 * differs from computeOffsetsFull() in that the number of tuples is \b not changed by
7595 * \throw If \a this is not allocated.
7596 * \throw If \a this->getNumberOfComponents() != 1.
7599 * - Before \a this contains [3,5,1,2,0,8]
7600 * - After \a this contains [0,3,8,9,11,11]<br>
7601 * Note that the last element 19 = 11 + 8 is missing because size of \a this
7602 * array is retained and thus there is no space to store the last element.
7604 void DataArrayInt::computeOffsets()
7607 if(getNumberOfComponents()!=1)
7608 throw INTERP_KERNEL::Exception("DataArrayInt::computeOffsets : only single component allowed !");
7609 int nbOfTuples=getNumberOfTuples();
7612 int *work=getPointer();
7615 for(int i=1;i<nbOfTuples;i++)
7618 work[i]=work[i-1]+tmp;
7626 * Modifies \a this one-dimensional array so that value of each element \a x
7627 * of \a this array (\a a) is computed as \f$ x_i = \sum_{j=0}^{i-1} a[ j ] \f$.
7628 * Or: for each i>0 new[i]=new[i-1]+old[i-1] for i==0 new[i]=0. Number
7629 * components remains the same and number of tuples is inceamented by one.<br>
7630 * This method is useful for allToAllV in MPI with contiguous policy. This method
7631 * differs from computeOffsets() in that the number of tuples is changed by this one.
7632 * This method preforms the reverse operation of DataArrayInt::deltaShiftIndex.
7633 * \throw If \a this is not allocated.
7634 * \throw If \a this->getNumberOfComponents() != 1.
7637 * - Before \a this contains [3,5,1,2,0,8]
7638 * - After \a this contains [0,3,8,9,11,11,19]<br>
7639 * \sa DataArrayInt::deltaShiftIndex
7641 void DataArrayInt::computeOffsetsFull()
7644 if(getNumberOfComponents()!=1)
7645 throw INTERP_KERNEL::Exception("DataArrayInt::computeOffsetsFull : only single component allowed !");
7646 int nbOfTuples=getNumberOfTuples();
7647 int *ret=(int *)malloc((nbOfTuples+1)*sizeof(int));
7648 const int *work=getConstPointer();
7650 for(int i=0;i<nbOfTuples;i++)
7651 ret[i+1]=work[i]+ret[i];
7652 useArray(ret,true,C_DEALLOC,nbOfTuples+1,1);
7657 * Returns two new DataArrayInt instances whose contents is computed from that of \a this and \a listOfIds arrays as follows.
7658 * \a this is expected to be an offset format ( as returned by DataArrayInt::computeOffsetsFull ) that is to say with one component
7659 * and ** sorted strictly increasingly **. \a listOfIds is expected to be sorted ascendingly (not strictly needed for \a listOfIds).
7660 * This methods searches in \a this, considered as a set of contiguous \c this->getNumberOfComponents() ranges, all ids in \a listOfIds
7661 * filling completely one of the ranges in \a this.
7663 * \param [in] listOfIds a list of ids that has to be sorted ascendingly.
7664 * \param [out] rangeIdsFetched the range ids fetched
7665 * \param [out] idsInInputListThatFetch contains the list of ids in \a listOfIds that are \b fully included in a range in \a this. So
7666 * \a idsInInputListThatFetch is a part of input \a listOfIds.
7668 * \sa DataArrayInt::computeOffsetsFull
7671 * - \a this : [0,3,7,9,15,18]
7672 * - \a listOfIds contains [0,1,2,3,7,8,15,16,17]
7673 * - \a rangeIdsFetched result array: [0,2,4]
7674 * - \a idsInInputListThatFetch result array: [0,1,2,7,8,15,16,17]
7675 * In this example id 3 in input \a listOfIds is alone so it do not appear in output \a idsInInputListThatFetch.
7678 void DataArrayInt::findIdsRangesInListOfIds(const DataArrayInt *listOfIds, DataArrayInt *& rangeIdsFetched, DataArrayInt *& idsInInputListThatFetch) const
7681 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsRangesInListOfIds : input list of ids is null !");
7682 listOfIds->checkAllocated(); checkAllocated();
7683 if(listOfIds->getNumberOfComponents()!=1)
7684 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsRangesInListOfIds : input list of ids must have exactly one component !");
7685 if(getNumberOfComponents()!=1)
7686 throw INTERP_KERNEL::Exception("DataArrayInt::findIdsRangesInListOfIds : this must have exactly one component !");
7687 MCAuto<DataArrayInt> ret0=DataArrayInt::New(); ret0->alloc(0,1);
7688 MCAuto<DataArrayInt> ret1=DataArrayInt::New(); ret1->alloc(0,1);
7689 const int *tupEnd(listOfIds->end()),*offBg(begin()),*offEnd(end()-1);
7690 const int *tupPtr(listOfIds->begin()),*offPtr(offBg);
7691 while(tupPtr!=tupEnd && offPtr!=offEnd)
7693 if(*tupPtr==*offPtr)
7696 while(i<offPtr[1] && *tupPtr==i && tupPtr!=tupEnd) { i++; tupPtr++; }
7699 ret0->pushBackSilent((int)std::distance(offBg,offPtr));
7700 ret1->pushBackValsSilent(tupPtr-(offPtr[1]-offPtr[0]),tupPtr);
7705 { if(*tupPtr<*offPtr) tupPtr++; else offPtr++; }
7707 rangeIdsFetched=ret0.retn();
7708 idsInInputListThatFetch=ret1.retn();
7712 * Returns a new DataArrayInt whose contents is computed from that of \a this and \a
7713 * offsets arrays as follows. \a offsets is a one-dimensional array considered as an
7714 * "index" array of a "iota" array, thus, whose each element gives an index of a group
7715 * beginning within the "iota" array. And \a this is a one-dimensional array
7716 * considered as a selector of groups described by \a offsets to include into the result array.
7717 * \throw If \a offsets is NULL.
7718 * \throw If \a offsets is not allocated.
7719 * \throw If \a offsets->getNumberOfComponents() != 1.
7720 * \throw If \a offsets is not monotonically increasing.
7721 * \throw If \a this is not allocated.
7722 * \throw If \a this->getNumberOfComponents() != 1.
7723 * \throw If any element of \a this is not a valid index for \a offsets array.
7726 * - \a this: [0,2,3]
7727 * - \a offsets: [0,3,6,10,14,20]
7728 * - result array: [0,1,2,6,7,8,9,10,11,12,13] == <br>
7729 * \c range(0,3) + \c range(6,10) + \c range(10,14) ==<br>
7730 * \c range( \a offsets[ \a this[0] ], offsets[ \a this[0]+1 ]) +
7731 * \c range( \a offsets[ \a this[1] ], offsets[ \a this[1]+1 ]) +
7732 * \c range( \a offsets[ \a this[2] ], offsets[ \a this[2]+1 ])
7734 DataArrayInt *DataArrayInt::buildExplicitArrByRanges(const DataArrayInt *offsets) const
7737 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrByRanges : DataArrayInt pointer in input is NULL !");
7739 if(getNumberOfComponents()!=1)
7740 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrByRanges : only single component allowed !");
7741 offsets->checkAllocated();
7742 if(offsets->getNumberOfComponents()!=1)
7743 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrByRanges : input array should have only single component !");
7744 int othNbTuples=offsets->getNumberOfTuples()-1;
7745 int nbOfTuples=getNumberOfTuples();
7746 int retNbOftuples=0;
7747 const int *work=getConstPointer();
7748 const int *offPtr=offsets->getConstPointer();
7749 for(int i=0;i<nbOfTuples;i++)
7752 if(val>=0 && val<othNbTuples)
7754 int delta=offPtr[val+1]-offPtr[val];
7756 retNbOftuples+=delta;
7759 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrByRanges : Tuple #" << val << " of offset array has a delta < 0 !";
7760 throw INTERP_KERNEL::Exception(oss.str().c_str());
7765 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrByRanges : Tuple #" << i << " in this contains " << val;
7766 oss << " whereas offsets array is of size " << othNbTuples+1 << " !";
7767 throw INTERP_KERNEL::Exception(oss.str().c_str());
7770 MCAuto<DataArrayInt> ret=DataArrayInt::New();
7771 ret->alloc(retNbOftuples,1);
7772 int *retPtr=ret->getPointer();
7773 for(int i=0;i<nbOfTuples;i++)
7776 int start=offPtr[val];
7777 int off=offPtr[val+1]-start;
7778 for(int j=0;j<off;j++,retPtr++)
7785 * Returns a new DataArrayInt whose contents is computed using \a this that must be a
7786 * scaled array (monotonically increasing).
7787 from that of \a this and \a
7788 * offsets arrays as follows. \a offsets is a one-dimensional array considered as an
7789 * "index" array of a "iota" array, thus, whose each element gives an index of a group
7790 * beginning within the "iota" array. And \a this is a one-dimensional array
7791 * considered as a selector of groups described by \a offsets to include into the result array.
7792 * \throw If \a is NULL.
7793 * \throw If \a this is not allocated.
7794 * \throw If \a this->getNumberOfComponents() != 1.
7795 * \throw If \a this->getNumberOfTuples() == 0.
7796 * \throw If \a this is not monotonically increasing.
7797 * \throw If any element of ids in ( \a bg \a stop \a step ) points outside the scale in \a this.
7800 * - \a bg , \a stop and \a step : (0,5,2)
7801 * - \a this: [0,3,6,10,14,20]
7802 * - result array: [0,0,0, 2,2,2,2, 4,4,4,4,4,4] == <br>
7804 DataArrayInt *DataArrayInt::buildExplicitArrOfSliceOnScaledArr(int bg, int stop, int step) const
7807 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrOfSliceOnScaledArr : not allocated array !");
7808 if(getNumberOfComponents()!=1)
7809 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrOfSliceOnScaledArr : number of components is expected to be equal to one !");
7810 int nbOfTuples(getNumberOfTuples());
7812 throw INTERP_KERNEL::Exception("DataArrayInt::buildExplicitArrOfSliceOnScaledArr : number of tuples must be != 0 !");
7813 const int *ids(begin());
7814 int nbOfEltsInSlc(GetNumberOfItemGivenBESRelative(bg,stop,step,"DataArrayInt::buildExplicitArrOfSliceOnScaledArr")),sz(0),pos(bg);
7815 for(int i=0;i<nbOfEltsInSlc;i++,pos+=step)
7817 if(pos>=0 && pos<nbOfTuples-1)
7819 int delta(ids[pos+1]-ids[pos]);
7823 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrOfSliceOnScaledArr : At pos #" << i << " of input slice, value is " << pos << " and at this pos this is not monotonically increasing !";
7824 throw INTERP_KERNEL::Exception(oss.str().c_str());
7829 std::ostringstream oss; oss << "DataArrayInt::buildExplicitArrOfSliceOnScaledArr : At pos #" << i << " of input slice, value is " << pos << " should be in [0," << nbOfTuples-1 << ") !";
7830 throw INTERP_KERNEL::Exception(oss.str().c_str());
7833 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(sz,1);
7834 int *retPtr(ret->getPointer());
7836 for(int i=0;i<nbOfEltsInSlc;i++,pos+=step)
7838 int delta(ids[pos+1]-ids[pos]);
7839 for(int j=0;j<delta;j++,retPtr++)
7846 * 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.
7847 * 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
7848 * in tuple **i** of returned DataArrayInt.
7849 * If ranges overlapped (in theory it should not) this method do not detect it and always returns the first range.
7851 * 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)]
7852 * The return DataArrayInt will contain : **[0,4,1,2,2,3]**
7854 * \param [in] ranges typically come from output of MEDCouplingUMesh::ComputeRangesFromTypeDistribution. Each range is specified like this : 1st component is
7855 * for lower value included and 2nd component is the upper value of corresponding range **excluded**.
7856 * \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
7857 * is thrown if no ranges in \a ranges contains value in \a this.
7859 * \sa DataArrayInt::findIdInRangeForEachTuple
7861 DataArrayInt *DataArrayInt::findRangeIdForEachTuple(const DataArrayInt *ranges) const
7864 throw INTERP_KERNEL::Exception("DataArrayInt::findRangeIdForEachTuple : null input pointer !");
7865 if(ranges->getNumberOfComponents()!=2)
7866 throw INTERP_KERNEL::Exception("DataArrayInt::findRangeIdForEachTuple : input DataArrayInt instance should have 2 components !");
7868 if(getNumberOfComponents()!=1)
7869 throw INTERP_KERNEL::Exception("DataArrayInt::findRangeIdForEachTuple : this should have only one component !");
7870 int nbTuples=getNumberOfTuples();
7871 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbTuples,1);
7872 int nbOfRanges=ranges->getNumberOfTuples();
7873 const int *rangesPtr=ranges->getConstPointer();
7874 int *retPtr=ret->getPointer();
7875 const int *inPtr=getConstPointer();
7876 for(int i=0;i<nbTuples;i++,retPtr++)
7880 for(int j=0;j<nbOfRanges && !found;j++)
7881 if(val>=rangesPtr[2*j] && val<rangesPtr[2*j+1])
7882 { *retPtr=j; found=true; }
7887 std::ostringstream oss; oss << "DataArrayInt::findRangeIdForEachTuple : tuple #" << i << " not found by any ranges !";
7888 throw INTERP_KERNEL::Exception(oss.str().c_str());
7895 * 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.
7896 * 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
7897 * in tuple **i** of returned DataArrayInt.
7898 * If ranges overlapped (in theory it should not) this method do not detect it and always returns the sub position of the first range.
7900 * 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)]
7901 * The return DataArrayInt will contain : **[1,2,4,0,2,2]**
7902 * This method is often called in pair with DataArrayInt::findRangeIdForEachTuple method.
7904 * \param [in] ranges typically come from output of MEDCouplingUMesh::ComputeRangesFromTypeDistribution. Each range is specified like this : 1st component is
7905 * for lower value included and 2nd component is the upper value of corresponding range **excluded**.
7906 * \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
7907 * is thrown if no ranges in \a ranges contains value in \a this.
7908 * \sa DataArrayInt::findRangeIdForEachTuple
7910 DataArrayInt *DataArrayInt::findIdInRangeForEachTuple(const DataArrayInt *ranges) const
7913 throw INTERP_KERNEL::Exception("DataArrayInt::findIdInRangeForEachTuple : null input pointer !");
7914 if(ranges->getNumberOfComponents()!=2)
7915 throw INTERP_KERNEL::Exception("DataArrayInt::findIdInRangeForEachTuple : input DataArrayInt instance should have 2 components !");
7917 if(getNumberOfComponents()!=1)
7918 throw INTERP_KERNEL::Exception("DataArrayInt::findIdInRangeForEachTuple : this should have only one component !");
7919 int nbTuples=getNumberOfTuples();
7920 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbTuples,1);
7921 int nbOfRanges=ranges->getNumberOfTuples();
7922 const int *rangesPtr=ranges->getConstPointer();
7923 int *retPtr=ret->getPointer();
7924 const int *inPtr=getConstPointer();
7925 for(int i=0;i<nbTuples;i++,retPtr++)
7929 for(int j=0;j<nbOfRanges && !found;j++)
7930 if(val>=rangesPtr[2*j] && val<rangesPtr[2*j+1])
7931 { *retPtr=val-rangesPtr[2*j]; found=true; }
7936 std::ostringstream oss; oss << "DataArrayInt::findIdInRangeForEachTuple : tuple #" << i << " not found by any ranges !";
7937 throw INTERP_KERNEL::Exception(oss.str().c_str());
7944 * \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).
7945 * 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).
7946 * 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 !
7947 * If this method has correctly worked, \a this will be able to be considered as a linked list.
7948 * This method does nothing if number of tuples is lower of equal to 1.
7950 * This method is useful for users having an unstructured mesh having only SEG2 to rearrange internaly the connectibity without any coordinates consideration.
7952 * \sa MEDCouplingUMesh::orderConsecutiveCells1D, DataArrayInt::fromLinkedListOfPairToList
7954 void DataArrayInt::sortEachPairToMakeALinkedList()
7957 if(getNumberOfComponents()!=2)
7958 throw INTERP_KERNEL::Exception("DataArrayInt::sortEachPairToMakeALinkedList : Only works on DataArrayInt instance with nb of components equal to 2 !");
7959 int nbOfTuples(getNumberOfTuples());
7962 int *conn(getPointer());
7963 for(int i=1;i<nbOfTuples;i++,conn+=2)
7967 if(conn[2]==conn[3])
7969 std::ostringstream oss; oss << "DataArrayInt::sortEachPairToMakeALinkedList : In the tuple #" << i << " presence of a pair filled with same ids !";
7970 throw INTERP_KERNEL::Exception(oss.str().c_str());
7972 if(conn[2]!=conn[1] && conn[3]==conn[1] && conn[2]!=conn[0])
7973 std::swap(conn[2],conn[3]);
7974 //not(conn[2]==conn[1] && conn[3]!=conn[1] && conn[3]!=conn[0])
7975 if(conn[2]!=conn[1] || conn[3]==conn[1] || conn[3]==conn[0])
7977 std::ostringstream oss; oss << "DataArrayInt::sortEachPairToMakeALinkedList : In the tuple #" << i << " something is invalid !";
7978 throw INTERP_KERNEL::Exception(oss.str().c_str());
7983 if(conn[0]==conn[1] || conn[2]==conn[3])
7984 throw INTERP_KERNEL::Exception("DataArrayInt::sortEachPairToMakeALinkedList : In the 2 first tuples presence of a pair filled with same ids !");
7987 s.insert(conn,conn+4);
7989 throw INTERP_KERNEL::Exception("DataArrayInt::sortEachPairToMakeALinkedList : This can't be considered as a linked list regarding 2 first tuples !");
7990 if(std::count(conn,conn+4,conn[0])==2)
7995 if(conn[2]==conn[0])
7999 std::copy(tmp,tmp+4,conn);
8002 {//here we are sure to have (std::count(conn,conn+4,conn[1])==2)
8003 if(conn[1]==conn[3])
8004 std::swap(conn[2],conn[3]);
8011 * \a this is expected to be a correctly linked list of pairs.
8013 * \sa DataArrayInt::sortEachPairToMakeALinkedList
8015 MCAuto<DataArrayInt> DataArrayInt::fromLinkedListOfPairToList() const
8018 checkNbOfComps(2,"DataArrayInt::fromLinkedListOfPairToList : this is expected to have 2 components");
8019 int nbTuples(getNumberOfTuples());
8021 throw INTERP_KERNEL::Exception("DataArrayInt::fromLinkedListOfPairToList : no tuples in this ! Not a linked list !");
8022 MCAuto<DataArrayInt> ret(DataArrayInt::New()); ret->alloc(nbTuples+1,1);
8023 const int *thisPtr(begin());
8024 int *retPtr(ret->getPointer());
8025 retPtr[0]=thisPtr[0];
8026 for(int i=0;i<nbTuples;i++)
8028 retPtr[i+1]=thisPtr[2*i+1];
8030 if(thisPtr[2*i+1]!=thisPtr[2*(i+1)+0])
8032 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 ?";
8033 throw INTERP_KERNEL::Exception(oss.str());
8041 * \param [in] nbTimes specifies the nb of times each tuples in \a this will be duplicated contiguouly in returned DataArrayInt instance.
8042 * \a nbTimes should be at least equal to 1.
8043 * \return a newly allocated DataArrayInt having one component and number of tuples equal to \a nbTimes * \c this->getNumberOfTuples.
8044 * \throw if \a this is not allocated or if \a this has not number of components set to one or if \a nbTimes is lower than 1.
8046 DataArrayInt *DataArrayInt::duplicateEachTupleNTimes(int nbTimes) const
8049 if(getNumberOfComponents()!=1)
8050 throw INTERP_KERNEL::Exception("DataArrayInt::duplicateEachTupleNTimes : this should have only one component !");
8052 throw INTERP_KERNEL::Exception("DataArrayInt::duplicateEachTupleNTimes : nb times should be >= 1 !");
8053 int nbTuples=getNumberOfTuples();
8054 const int *inPtr=getConstPointer();
8055 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbTimes*nbTuples,1);
8056 int *retPtr=ret->getPointer();
8057 for(int i=0;i<nbTuples;i++,inPtr++)
8060 for(int j=0;j<nbTimes;j++,retPtr++)
8063 ret->copyStringInfoFrom(*this);
8068 * This method returns all different values found in \a this. This method throws if \a this has not been allocated.
8069 * But the number of components can be different from one.
8070 * \return a newly allocated array (that should be dealt by the caller) containing different values in \a this.
8072 DataArrayInt *DataArrayInt::getDifferentValues() const
8076 ret.insert(begin(),end());
8077 MCAuto<DataArrayInt> ret2=DataArrayInt::New(); ret2->alloc((int)ret.size(),1);
8078 std::copy(ret.begin(),ret.end(),ret2->getPointer());
8083 * This method is a refinement of DataArrayInt::getDifferentValues because it returns not only different values in \a this but also, for each of
8084 * them it tells which tuple id have this id.
8085 * This method works only on arrays with one component (if it is not the case call DataArrayInt::rearrange(1) ).
8086 * This method returns two arrays having same size.
8087 * 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.
8088 * 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]]
8090 std::vector<DataArrayInt *> DataArrayInt::partitionByDifferentValues(std::vector<int>& differentIds) const
8093 if(getNumberOfComponents()!=1)
8094 throw INTERP_KERNEL::Exception("DataArrayInt::partitionByDifferentValues : this should have only one component !");
8096 std::map<int,int> m,m2,m3;
8097 for(const int *w=begin();w!=end();w++)
8099 differentIds.resize(m.size());
8100 std::vector<DataArrayInt *> ret(m.size());
8101 std::vector<int *> retPtr(m.size());
8102 for(std::map<int,int>::const_iterator it=m.begin();it!=m.end();it++,id++)
8105 ret[id]=DataArrayInt::New();
8106 ret[id]->alloc((*it).second,1);
8107 retPtr[id]=ret[id]->getPointer();
8108 differentIds[id]=(*it).first;
8111 for(const int *w=begin();w!=end();w++,id++)
8113 retPtr[m2[*w]][m3[*w]++]=id;
8119 * This method split ids in [0, \c this->getNumberOfTuples() ) using \a this array as a field of weight (>=0 each).
8120 * The aim of this method is to return a set of \a nbOfSlices chunk of contiguous ids as balanced as possible.
8122 * \param [in] nbOfSlices - number of slices expected.
8123 * \return - a vector having a size equal to \a nbOfSlices giving the start (included) and the stop (excluded) of each chunks.
8125 * \sa DataArray::GetSlice
8126 * \throw If \a this is not allocated or not with exactly one component.
8127 * \throw If an element in \a this if < 0.
8129 std::vector< std::pair<int,int> > DataArrayInt::splitInBalancedSlices(int nbOfSlices) const
8131 if(!isAllocated() || getNumberOfComponents()!=1)
8132 throw INTERP_KERNEL::Exception("DataArrayInt::splitInBalancedSlices : this array should have number of components equal to one and must be allocated !");
8134 throw INTERP_KERNEL::Exception("DataArrayInt::splitInBalancedSlices : number of slices must be >= 1 !");
8135 int sum(accumulate(0)),nbOfTuples(getNumberOfTuples());
8136 int sumPerSlc(sum/nbOfSlices),pos(0);
8137 const int *w(begin());
8138 std::vector< std::pair<int,int> > ret(nbOfSlices);
8139 for(int i=0;i<nbOfSlices;i++)
8141 std::pair<int,int> p(pos,-1);
8143 while(locSum<sumPerSlc && pos<nbOfTuples) { pos++; locSum+=*w++; }
8147 p.second=nbOfTuples;
8154 * Returns a new DataArrayInt that is a sum of two given arrays. There are 3
8156 * 1. The arrays have same number of tuples and components. Then each value of
8157 * the result array (_a_) is a sum of the corresponding values of \a a1 and \a a2,
8158 * i.e.: _a_ [ i, j ] = _a1_ [ i, j ] + _a2_ [ i, j ].
8159 * 2. The arrays have same number of tuples and one array, say _a2_, has one
8161 * _a_ [ i, j ] = _a1_ [ i, j ] + _a2_ [ i, 0 ].
8162 * 3. The arrays have same number of components and one array, say _a2_, has one
8164 * _a_ [ i, j ] = _a1_ [ i, j ] + _a2_ [ 0, j ].
8166 * Info on components is copied either from the first array (in the first case) or from
8167 * the array with maximal number of elements (getNbOfElems()).
8168 * \param [in] a1 - an array to sum up.
8169 * \param [in] a2 - another array to sum up.
8170 * \return DataArrayInt * - the new instance of DataArrayInt.
8171 * The caller is to delete this result array using decrRef() as it is no more
8173 * \throw If either \a a1 or \a a2 is NULL.
8174 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
8175 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
8176 * none of them has number of tuples or components equal to 1.
8178 DataArrayInt *DataArrayInt::Add(const DataArrayInt *a1, const DataArrayInt *a2)
8181 throw INTERP_KERNEL::Exception("DataArrayInt::Add : input DataArrayInt instance is NULL !");
8182 int nbOfTuple=a1->getNumberOfTuples();
8183 int nbOfTuple2=a2->getNumberOfTuples();
8184 int nbOfComp=a1->getNumberOfComponents();
8185 int nbOfComp2=a2->getNumberOfComponents();
8186 MCAuto<DataArrayInt> ret=0;
8187 if(nbOfTuple==nbOfTuple2)
8189 if(nbOfComp==nbOfComp2)
8191 ret=DataArrayInt::New();
8192 ret->alloc(nbOfTuple,nbOfComp);
8193 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::plus<int>());
8194 ret->copyStringInfoFrom(*a1);
8198 int nbOfCompMin,nbOfCompMax;
8199 const DataArrayInt *aMin, *aMax;
8200 if(nbOfComp>nbOfComp2)
8202 nbOfCompMin=nbOfComp2; nbOfCompMax=nbOfComp;
8207 nbOfCompMin=nbOfComp; nbOfCompMax=nbOfComp2;
8212 ret=DataArrayInt::New();
8213 ret->alloc(nbOfTuple,nbOfCompMax);
8214 const int *aMinPtr=aMin->getConstPointer();
8215 const int *aMaxPtr=aMax->getConstPointer();
8216 int *res=ret->getPointer();
8217 for(int i=0;i<nbOfTuple;i++)
8218 res=std::transform(aMaxPtr+i*nbOfCompMax,aMaxPtr+(i+1)*nbOfCompMax,res,std::bind2nd(std::plus<int>(),aMinPtr[i]));
8219 ret->copyStringInfoFrom(*aMax);
8222 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Add !");
8225 else if((nbOfTuple==1 && nbOfTuple2>1) || (nbOfTuple>1 && nbOfTuple2==1))
8227 if(nbOfComp==nbOfComp2)
8229 int nbOfTupleMax=std::max(nbOfTuple,nbOfTuple2);
8230 const DataArrayInt *aMin=nbOfTuple>nbOfTuple2?a2:a1;
8231 const DataArrayInt *aMax=nbOfTuple>nbOfTuple2?a1:a2;
8232 const int *aMinPtr=aMin->getConstPointer(),*aMaxPtr=aMax->getConstPointer();
8233 ret=DataArrayInt::New();
8234 ret->alloc(nbOfTupleMax,nbOfComp);
8235 int *res=ret->getPointer();
8236 for(int i=0;i<nbOfTupleMax;i++)
8237 res=std::transform(aMaxPtr+i*nbOfComp,aMaxPtr+(i+1)*nbOfComp,aMinPtr,res,std::plus<int>());
8238 ret->copyStringInfoFrom(*aMax);
8241 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Add !");
8244 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Add !");
8249 * Adds values of another DataArrayInt to values of \a this one. There are 3
8251 * 1. The arrays have same number of tuples and components. Then each value of
8252 * \a other array is added to the corresponding value of \a this array, i.e.:
8253 * _a_ [ i, j ] += _other_ [ i, j ].
8254 * 2. The arrays have same number of tuples and \a other array has one component. Then
8255 * _a_ [ i, j ] += _other_ [ i, 0 ].
8256 * 3. The arrays have same number of components and \a other array has one tuple. Then
8257 * _a_ [ i, j ] += _a2_ [ 0, j ].
8259 * \param [in] other - an array to add to \a this one.
8260 * \throw If \a other is NULL.
8261 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
8262 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
8263 * \a other has number of both tuples and components not equal to 1.
8265 void DataArrayInt::addEqual(const DataArrayInt *other)
8268 throw INTERP_KERNEL::Exception("DataArrayInt::addEqual : input DataArrayInt instance is NULL !");
8269 const char *msg="Nb of tuples mismatch for DataArrayInt::addEqual !";
8270 checkAllocated(); other->checkAllocated();
8271 int nbOfTuple=getNumberOfTuples();
8272 int nbOfTuple2=other->getNumberOfTuples();
8273 int nbOfComp=getNumberOfComponents();
8274 int nbOfComp2=other->getNumberOfComponents();
8275 if(nbOfTuple==nbOfTuple2)
8277 if(nbOfComp==nbOfComp2)
8279 std::transform(begin(),end(),other->begin(),getPointer(),std::plus<int>());
8281 else if(nbOfComp2==1)
8283 int *ptr=getPointer();
8284 const int *ptrc=other->getConstPointer();
8285 for(int i=0;i<nbOfTuple;i++)
8286 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::plus<int>(),*ptrc++));
8289 throw INTERP_KERNEL::Exception(msg);
8291 else if(nbOfTuple2==1)
8293 if(nbOfComp2==nbOfComp)
8295 int *ptr=getPointer();
8296 const int *ptrc=other->getConstPointer();
8297 for(int i=0;i<nbOfTuple;i++)
8298 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::plus<int>());
8301 throw INTERP_KERNEL::Exception(msg);
8304 throw INTERP_KERNEL::Exception(msg);
8309 * Returns a new DataArrayInt that is a subtraction of two given arrays. There are 3
8311 * 1. The arrays have same number of tuples and components. Then each value of
8312 * the result array (_a_) is a subtraction of the corresponding values of \a a1 and
8313 * \a a2, i.e.: _a_ [ i, j ] = _a1_ [ i, j ] - _a2_ [ i, j ].
8314 * 2. The arrays have same number of tuples and one array, say _a2_, has one
8316 * _a_ [ i, j ] = _a1_ [ i, j ] - _a2_ [ i, 0 ].
8317 * 3. The arrays have same number of components and one array, say _a2_, has one
8319 * _a_ [ i, j ] = _a1_ [ i, j ] - _a2_ [ 0, j ].
8321 * Info on components is copied either from the first array (in the first case) or from
8322 * the array with maximal number of elements (getNbOfElems()).
8323 * \param [in] a1 - an array to subtract from.
8324 * \param [in] a2 - an array to subtract.
8325 * \return DataArrayInt * - the new instance of DataArrayInt.
8326 * The caller is to delete this result array using decrRef() as it is no more
8328 * \throw If either \a a1 or \a a2 is NULL.
8329 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
8330 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
8331 * none of them has number of tuples or components equal to 1.
8333 DataArrayInt *DataArrayInt::Substract(const DataArrayInt *a1, const DataArrayInt *a2)
8336 throw INTERP_KERNEL::Exception("DataArrayInt::Substract : input DataArrayInt instance is NULL !");
8337 int nbOfTuple1=a1->getNumberOfTuples();
8338 int nbOfTuple2=a2->getNumberOfTuples();
8339 int nbOfComp1=a1->getNumberOfComponents();
8340 int nbOfComp2=a2->getNumberOfComponents();
8341 if(nbOfTuple2==nbOfTuple1)
8343 if(nbOfComp1==nbOfComp2)
8345 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8346 ret->alloc(nbOfTuple2,nbOfComp1);
8347 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::minus<int>());
8348 ret->copyStringInfoFrom(*a1);
8351 else if(nbOfComp2==1)
8353 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8354 ret->alloc(nbOfTuple1,nbOfComp1);
8355 const int *a2Ptr=a2->getConstPointer();
8356 const int *a1Ptr=a1->getConstPointer();
8357 int *res=ret->getPointer();
8358 for(int i=0;i<nbOfTuple1;i++)
8359 res=std::transform(a1Ptr+i*nbOfComp1,a1Ptr+(i+1)*nbOfComp1,res,std::bind2nd(std::minus<int>(),a2Ptr[i]));
8360 ret->copyStringInfoFrom(*a1);
8365 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Substract !");
8369 else if(nbOfTuple2==1)
8371 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Substract !");
8372 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8373 ret->alloc(nbOfTuple1,nbOfComp1);
8374 const int *a1ptr=a1->getConstPointer(),*a2ptr=a2->getConstPointer();
8375 int *pt=ret->getPointer();
8376 for(int i=0;i<nbOfTuple1;i++)
8377 pt=std::transform(a1ptr+i*nbOfComp1,a1ptr+(i+1)*nbOfComp1,a2ptr,pt,std::minus<int>());
8378 ret->copyStringInfoFrom(*a1);
8383 a1->checkNbOfTuples(nbOfTuple2,"Nb of tuples mismatch for array Substract !");//will always throw an exception
8389 * Subtract values of another DataArrayInt from values of \a this one. There are 3
8391 * 1. The arrays have same number of tuples and components. Then each value of
8392 * \a other array is subtracted from the corresponding value of \a this array, i.e.:
8393 * _a_ [ i, j ] -= _other_ [ i, j ].
8394 * 2. The arrays have same number of tuples and \a other array has one component. Then
8395 * _a_ [ i, j ] -= _other_ [ i, 0 ].
8396 * 3. The arrays have same number of components and \a other array has one tuple. Then
8397 * _a_ [ i, j ] -= _a2_ [ 0, j ].
8399 * \param [in] other - an array to subtract from \a this one.
8400 * \throw If \a other is NULL.
8401 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
8402 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
8403 * \a other has number of both tuples and components not equal to 1.
8405 void DataArrayInt::substractEqual(const DataArrayInt *other)
8408 throw INTERP_KERNEL::Exception("DataArrayInt::substractEqual : input DataArrayInt instance is NULL !");
8409 const char *msg="Nb of tuples mismatch for DataArrayInt::substractEqual !";
8410 checkAllocated(); other->checkAllocated();
8411 int nbOfTuple=getNumberOfTuples();
8412 int nbOfTuple2=other->getNumberOfTuples();
8413 int nbOfComp=getNumberOfComponents();
8414 int nbOfComp2=other->getNumberOfComponents();
8415 if(nbOfTuple==nbOfTuple2)
8417 if(nbOfComp==nbOfComp2)
8419 std::transform(begin(),end(),other->begin(),getPointer(),std::minus<int>());
8421 else if(nbOfComp2==1)
8423 int *ptr=getPointer();
8424 const int *ptrc=other->getConstPointer();
8425 for(int i=0;i<nbOfTuple;i++)
8426 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::minus<int>(),*ptrc++));
8429 throw INTERP_KERNEL::Exception(msg);
8431 else if(nbOfTuple2==1)
8433 int *ptr=getPointer();
8434 const int *ptrc=other->getConstPointer();
8435 for(int i=0;i<nbOfTuple;i++)
8436 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::minus<int>());
8439 throw INTERP_KERNEL::Exception(msg);
8444 * Returns a new DataArrayInt that is a product of two given arrays. There are 3
8446 * 1. The arrays have same number of tuples and components. Then each value of
8447 * the result array (_a_) is a product of the corresponding values of \a a1 and
8448 * \a a2, i.e.: _a_ [ i, j ] = _a1_ [ i, j ] * _a2_ [ i, j ].
8449 * 2. The arrays have same number of tuples and one array, say _a2_, has one
8451 * _a_ [ i, j ] = _a1_ [ i, j ] * _a2_ [ i, 0 ].
8452 * 3. The arrays have same number of components and one array, say _a2_, has one
8454 * _a_ [ i, j ] = _a1_ [ i, j ] * _a2_ [ 0, j ].
8456 * Info on components is copied either from the first array (in the first case) or from
8457 * the array with maximal number of elements (getNbOfElems()).
8458 * \param [in] a1 - a factor array.
8459 * \param [in] a2 - another factor array.
8460 * \return DataArrayInt * - the new instance of DataArrayInt.
8461 * The caller is to delete this result array using decrRef() as it is no more
8463 * \throw If either \a a1 or \a a2 is NULL.
8464 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
8465 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
8466 * none of them has number of tuples or components equal to 1.
8468 DataArrayInt *DataArrayInt::Multiply(const DataArrayInt *a1, const DataArrayInt *a2)
8471 throw INTERP_KERNEL::Exception("DataArrayInt::Multiply : input DataArrayInt instance is NULL !");
8472 int nbOfTuple=a1->getNumberOfTuples();
8473 int nbOfTuple2=a2->getNumberOfTuples();
8474 int nbOfComp=a1->getNumberOfComponents();
8475 int nbOfComp2=a2->getNumberOfComponents();
8476 MCAuto<DataArrayInt> ret=0;
8477 if(nbOfTuple==nbOfTuple2)
8479 if(nbOfComp==nbOfComp2)
8481 ret=DataArrayInt::New();
8482 ret->alloc(nbOfTuple,nbOfComp);
8483 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::multiplies<int>());
8484 ret->copyStringInfoFrom(*a1);
8488 int nbOfCompMin,nbOfCompMax;
8489 const DataArrayInt *aMin, *aMax;
8490 if(nbOfComp>nbOfComp2)
8492 nbOfCompMin=nbOfComp2; nbOfCompMax=nbOfComp;
8497 nbOfCompMin=nbOfComp; nbOfCompMax=nbOfComp2;
8502 ret=DataArrayInt::New();
8503 ret->alloc(nbOfTuple,nbOfCompMax);
8504 const int *aMinPtr=aMin->getConstPointer();
8505 const int *aMaxPtr=aMax->getConstPointer();
8506 int *res=ret->getPointer();
8507 for(int i=0;i<nbOfTuple;i++)
8508 res=std::transform(aMaxPtr+i*nbOfCompMax,aMaxPtr+(i+1)*nbOfCompMax,res,std::bind2nd(std::multiplies<int>(),aMinPtr[i]));
8509 ret->copyStringInfoFrom(*aMax);
8512 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Multiply !");
8515 else if((nbOfTuple==1 && nbOfTuple2>1) || (nbOfTuple>1 && nbOfTuple2==1))
8517 if(nbOfComp==nbOfComp2)
8519 int nbOfTupleMax=std::max(nbOfTuple,nbOfTuple2);
8520 const DataArrayInt *aMin=nbOfTuple>nbOfTuple2?a2:a1;
8521 const DataArrayInt *aMax=nbOfTuple>nbOfTuple2?a1:a2;
8522 const int *aMinPtr=aMin->getConstPointer(),*aMaxPtr=aMax->getConstPointer();
8523 ret=DataArrayInt::New();
8524 ret->alloc(nbOfTupleMax,nbOfComp);
8525 int *res=ret->getPointer();
8526 for(int i=0;i<nbOfTupleMax;i++)
8527 res=std::transform(aMaxPtr+i*nbOfComp,aMaxPtr+(i+1)*nbOfComp,aMinPtr,res,std::multiplies<int>());
8528 ret->copyStringInfoFrom(*aMax);
8531 throw INTERP_KERNEL::Exception("Nb of components mismatch for array Multiply !");
8534 throw INTERP_KERNEL::Exception("Nb of tuples mismatch for array Multiply !");
8540 * Multiply values of another DataArrayInt to values of \a this one. There are 3
8542 * 1. The arrays have same number of tuples and components. Then each value of
8543 * \a other array is multiplied to the corresponding value of \a this array, i.e.:
8544 * _a_ [ i, j ] *= _other_ [ i, j ].
8545 * 2. The arrays have same number of tuples and \a other array has one component. Then
8546 * _a_ [ i, j ] *= _other_ [ i, 0 ].
8547 * 3. The arrays have same number of components and \a other array has one tuple. Then
8548 * _a_ [ i, j ] *= _a2_ [ 0, j ].
8550 * \param [in] other - an array to multiply to \a this one.
8551 * \throw If \a other is NULL.
8552 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
8553 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
8554 * \a other has number of both tuples and components not equal to 1.
8556 void DataArrayInt::multiplyEqual(const DataArrayInt *other)
8559 throw INTERP_KERNEL::Exception("DataArrayInt::multiplyEqual : input DataArrayInt instance is NULL !");
8560 const char *msg="Nb of tuples mismatch for DataArrayInt::multiplyEqual !";
8561 checkAllocated(); other->checkAllocated();
8562 int nbOfTuple=getNumberOfTuples();
8563 int nbOfTuple2=other->getNumberOfTuples();
8564 int nbOfComp=getNumberOfComponents();
8565 int nbOfComp2=other->getNumberOfComponents();
8566 if(nbOfTuple==nbOfTuple2)
8568 if(nbOfComp==nbOfComp2)
8570 std::transform(begin(),end(),other->begin(),getPointer(),std::multiplies<int>());
8572 else if(nbOfComp2==1)
8574 int *ptr=getPointer();
8575 const int *ptrc=other->getConstPointer();
8576 for(int i=0;i<nbOfTuple;i++)
8577 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::multiplies<int>(),*ptrc++));
8580 throw INTERP_KERNEL::Exception(msg);
8582 else if(nbOfTuple2==1)
8584 if(nbOfComp2==nbOfComp)
8586 int *ptr=getPointer();
8587 const int *ptrc=other->getConstPointer();
8588 for(int i=0;i<nbOfTuple;i++)
8589 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::multiplies<int>());
8592 throw INTERP_KERNEL::Exception(msg);
8595 throw INTERP_KERNEL::Exception(msg);
8601 * Returns a new DataArrayInt that is a division of two given arrays. There are 3
8603 * 1. The arrays have same number of tuples and components. Then each value of
8604 * the result array (_a_) is a division of the corresponding values of \a a1 and
8605 * \a a2, i.e.: _a_ [ i, j ] = _a1_ [ i, j ] / _a2_ [ i, j ].
8606 * 2. The arrays have same number of tuples and one array, say _a2_, has one
8608 * _a_ [ i, j ] = _a1_ [ i, j ] / _a2_ [ i, 0 ].
8609 * 3. The arrays have same number of components and one array, say _a2_, has one
8611 * _a_ [ i, j ] = _a1_ [ i, j ] / _a2_ [ 0, j ].
8613 * Info on components is copied either from the first array (in the first case) or from
8614 * the array with maximal number of elements (getNbOfElems()).
8615 * \warning No check of division by zero is performed!
8616 * \param [in] a1 - a numerator array.
8617 * \param [in] a2 - a denominator array.
8618 * \return DataArrayInt * - the new instance of DataArrayInt.
8619 * The caller is to delete this result array using decrRef() as it is no more
8621 * \throw If either \a a1 or \a a2 is NULL.
8622 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
8623 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
8624 * none of them has number of tuples or components equal to 1.
8626 DataArrayInt *DataArrayInt::Divide(const DataArrayInt *a1, const DataArrayInt *a2)
8629 throw INTERP_KERNEL::Exception("DataArrayInt::Divide : input DataArrayInt instance is NULL !");
8630 int nbOfTuple1=a1->getNumberOfTuples();
8631 int nbOfTuple2=a2->getNumberOfTuples();
8632 int nbOfComp1=a1->getNumberOfComponents();
8633 int nbOfComp2=a2->getNumberOfComponents();
8634 if(nbOfTuple2==nbOfTuple1)
8636 if(nbOfComp1==nbOfComp2)
8638 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8639 ret->alloc(nbOfTuple2,nbOfComp1);
8640 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::divides<int>());
8641 ret->copyStringInfoFrom(*a1);
8644 else if(nbOfComp2==1)
8646 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8647 ret->alloc(nbOfTuple1,nbOfComp1);
8648 const int *a2Ptr=a2->getConstPointer();
8649 const int *a1Ptr=a1->getConstPointer();
8650 int *res=ret->getPointer();
8651 for(int i=0;i<nbOfTuple1;i++)
8652 res=std::transform(a1Ptr+i*nbOfComp1,a1Ptr+(i+1)*nbOfComp1,res,std::bind2nd(std::divides<int>(),a2Ptr[i]));
8653 ret->copyStringInfoFrom(*a1);
8658 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Divide !");
8662 else if(nbOfTuple2==1)
8664 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Divide !");
8665 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8666 ret->alloc(nbOfTuple1,nbOfComp1);
8667 const int *a1ptr=a1->getConstPointer(),*a2ptr=a2->getConstPointer();
8668 int *pt=ret->getPointer();
8669 for(int i=0;i<nbOfTuple1;i++)
8670 pt=std::transform(a1ptr+i*nbOfComp1,a1ptr+(i+1)*nbOfComp1,a2ptr,pt,std::divides<int>());
8671 ret->copyStringInfoFrom(*a1);
8676 a1->checkNbOfTuples(nbOfTuple2,"Nb of tuples mismatch for array Divide !");//will always throw an exception
8682 * Divide values of \a this array by values of another DataArrayInt. There are 3
8684 * 1. The arrays have same number of tuples and components. Then each value of
8685 * \a this array is divided by the corresponding value of \a other one, i.e.:
8686 * _a_ [ i, j ] /= _other_ [ i, j ].
8687 * 2. The arrays have same number of tuples and \a other array has one component. Then
8688 * _a_ [ i, j ] /= _other_ [ i, 0 ].
8689 * 3. The arrays have same number of components and \a other array has one tuple. Then
8690 * _a_ [ i, j ] /= _a2_ [ 0, j ].
8692 * \warning No check of division by zero is performed!
8693 * \param [in] other - an array to divide \a this one by.
8694 * \throw If \a other is NULL.
8695 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
8696 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
8697 * \a other has number of both tuples and components not equal to 1.
8699 void DataArrayInt::divideEqual(const DataArrayInt *other)
8702 throw INTERP_KERNEL::Exception("DataArrayInt::divideEqual : input DataArrayInt instance is NULL !");
8703 const char *msg="Nb of tuples mismatch for DataArrayInt::divideEqual !";
8704 checkAllocated(); other->checkAllocated();
8705 int nbOfTuple=getNumberOfTuples();
8706 int nbOfTuple2=other->getNumberOfTuples();
8707 int nbOfComp=getNumberOfComponents();
8708 int nbOfComp2=other->getNumberOfComponents();
8709 if(nbOfTuple==nbOfTuple2)
8711 if(nbOfComp==nbOfComp2)
8713 std::transform(begin(),end(),other->begin(),getPointer(),std::divides<int>());
8715 else if(nbOfComp2==1)
8717 int *ptr=getPointer();
8718 const int *ptrc=other->getConstPointer();
8719 for(int i=0;i<nbOfTuple;i++)
8720 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::divides<int>(),*ptrc++));
8723 throw INTERP_KERNEL::Exception(msg);
8725 else if(nbOfTuple2==1)
8727 if(nbOfComp2==nbOfComp)
8729 int *ptr=getPointer();
8730 const int *ptrc=other->getConstPointer();
8731 for(int i=0;i<nbOfTuple;i++)
8732 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::divides<int>());
8735 throw INTERP_KERNEL::Exception(msg);
8738 throw INTERP_KERNEL::Exception(msg);
8744 * Returns a new DataArrayInt that is a modulus of two given arrays. There are 3
8746 * 1. The arrays have same number of tuples and components. Then each value of
8747 * the result array (_a_) is a division of the corresponding values of \a a1 and
8748 * \a a2, i.e.: _a_ [ i, j ] = _a1_ [ i, j ] % _a2_ [ i, j ].
8749 * 2. The arrays have same number of tuples and one array, say _a2_, has one
8751 * _a_ [ i, j ] = _a1_ [ i, j ] % _a2_ [ i, 0 ].
8752 * 3. The arrays have same number of components and one array, say _a2_, has one
8754 * _a_ [ i, j ] = _a1_ [ i, j ] % _a2_ [ 0, j ].
8756 * Info on components is copied either from the first array (in the first case) or from
8757 * the array with maximal number of elements (getNbOfElems()).
8758 * \warning No check of division by zero is performed!
8759 * \param [in] a1 - a dividend array.
8760 * \param [in] a2 - a divisor array.
8761 * \return DataArrayInt * - the new instance of DataArrayInt.
8762 * The caller is to delete this result array using decrRef() as it is no more
8764 * \throw If either \a a1 or \a a2 is NULL.
8765 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples() and
8766 * \a a1->getNumberOfComponents() != \a a2->getNumberOfComponents() and
8767 * none of them has number of tuples or components equal to 1.
8769 DataArrayInt *DataArrayInt::Modulus(const DataArrayInt *a1, const DataArrayInt *a2)
8772 throw INTERP_KERNEL::Exception("DataArrayInt::Modulus : input DataArrayInt instance is NULL !");
8773 int nbOfTuple1=a1->getNumberOfTuples();
8774 int nbOfTuple2=a2->getNumberOfTuples();
8775 int nbOfComp1=a1->getNumberOfComponents();
8776 int nbOfComp2=a2->getNumberOfComponents();
8777 if(nbOfTuple2==nbOfTuple1)
8779 if(nbOfComp1==nbOfComp2)
8781 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8782 ret->alloc(nbOfTuple2,nbOfComp1);
8783 std::transform(a1->begin(),a1->end(),a2->begin(),ret->getPointer(),std::modulus<int>());
8784 ret->copyStringInfoFrom(*a1);
8787 else if(nbOfComp2==1)
8789 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8790 ret->alloc(nbOfTuple1,nbOfComp1);
8791 const int *a2Ptr=a2->getConstPointer();
8792 const int *a1Ptr=a1->getConstPointer();
8793 int *res=ret->getPointer();
8794 for(int i=0;i<nbOfTuple1;i++)
8795 res=std::transform(a1Ptr+i*nbOfComp1,a1Ptr+(i+1)*nbOfComp1,res,std::bind2nd(std::modulus<int>(),a2Ptr[i]));
8796 ret->copyStringInfoFrom(*a1);
8801 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Modulus !");
8805 else if(nbOfTuple2==1)
8807 a1->checkNbOfComps(nbOfComp2,"Nb of components mismatch for array Modulus !");
8808 MCAuto<DataArrayInt> ret=DataArrayInt::New();
8809 ret->alloc(nbOfTuple1,nbOfComp1);
8810 const int *a1ptr=a1->getConstPointer(),*a2ptr=a2->getConstPointer();
8811 int *pt=ret->getPointer();
8812 for(int i=0;i<nbOfTuple1;i++)
8813 pt=std::transform(a1ptr+i*nbOfComp1,a1ptr+(i+1)*nbOfComp1,a2ptr,pt,std::modulus<int>());
8814 ret->copyStringInfoFrom(*a1);
8819 a1->checkNbOfTuples(nbOfTuple2,"Nb of tuples mismatch for array Modulus !");//will always throw an exception
8825 * Modify \a this array so that each value becomes a modulus of division of this value by
8826 * a value of another DataArrayInt. There are 3 valid cases.
8827 * 1. The arrays have same number of tuples and components. Then each value of
8828 * \a this array is divided by the corresponding value of \a other one, i.e.:
8829 * _a_ [ i, j ] %= _other_ [ i, j ].
8830 * 2. The arrays have same number of tuples and \a other array has one component. Then
8831 * _a_ [ i, j ] %= _other_ [ i, 0 ].
8832 * 3. The arrays have same number of components and \a other array has one tuple. Then
8833 * _a_ [ i, j ] %= _a2_ [ 0, j ].
8835 * \warning No check of division by zero is performed!
8836 * \param [in] other - a divisor array.
8837 * \throw If \a other is NULL.
8838 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples() and
8839 * \a this->getNumberOfComponents() != \a other->getNumberOfComponents() and
8840 * \a other has number of both tuples and components not equal to 1.
8842 void DataArrayInt::modulusEqual(const DataArrayInt *other)
8845 throw INTERP_KERNEL::Exception("DataArrayInt::modulusEqual : input DataArrayInt instance is NULL !");
8846 const char *msg="Nb of tuples mismatch for DataArrayInt::modulusEqual !";
8847 checkAllocated(); other->checkAllocated();
8848 int nbOfTuple=getNumberOfTuples();
8849 int nbOfTuple2=other->getNumberOfTuples();
8850 int nbOfComp=getNumberOfComponents();
8851 int nbOfComp2=other->getNumberOfComponents();
8852 if(nbOfTuple==nbOfTuple2)
8854 if(nbOfComp==nbOfComp2)
8856 std::transform(begin(),end(),other->begin(),getPointer(),std::modulus<int>());
8858 else if(nbOfComp2==1)
8860 if(nbOfComp2==nbOfComp)
8862 int *ptr=getPointer();
8863 const int *ptrc=other->getConstPointer();
8864 for(int i=0;i<nbOfTuple;i++)
8865 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptr+i*nbOfComp,std::bind2nd(std::modulus<int>(),*ptrc++));
8868 throw INTERP_KERNEL::Exception(msg);
8871 throw INTERP_KERNEL::Exception(msg);
8873 else if(nbOfTuple2==1)
8875 int *ptr=getPointer();
8876 const int *ptrc=other->getConstPointer();
8877 for(int i=0;i<nbOfTuple;i++)
8878 std::transform(ptr+i*nbOfComp,ptr+(i+1)*nbOfComp,ptrc,ptr+i*nbOfComp,std::modulus<int>());
8881 throw INTERP_KERNEL::Exception(msg);
8886 * Returns a new DataArrayInt that is the result of pow of two given arrays. There are 3
8889 * \param [in] a1 - an array to pow up.
8890 * \param [in] a2 - another array to sum up.
8891 * \return DataArrayInt * - the new instance of DataArrayInt.
8892 * The caller is to delete this result array using decrRef() as it is no more
8894 * \throw If either \a a1 or \a a2 is NULL.
8895 * \throw If \a a1->getNumberOfTuples() != \a a2->getNumberOfTuples()
8896 * \throw If \a a1->getNumberOfComponents() != 1 or \a a2->getNumberOfComponents() != 1.
8897 * \throw If there is a negative value in \a a2.
8899 DataArrayInt *DataArrayInt::Pow(const DataArrayInt *a1, const DataArrayInt *a2)
8902 throw INTERP_KERNEL::Exception("DataArrayInt::Pow : at least one of input instances is null !");
8903 int nbOfTuple=a1->getNumberOfTuples();
8904 int nbOfTuple2=a2->getNumberOfTuples();
8905 int nbOfComp=a1->getNumberOfComponents();
8906 int nbOfComp2=a2->getNumberOfComponents();
8907 if(nbOfTuple!=nbOfTuple2)
8908 throw INTERP_KERNEL::Exception("DataArrayInt::Pow : number of tuples mismatches !");
8909 if(nbOfComp!=1 || nbOfComp2!=1)
8910 throw INTERP_KERNEL::Exception("DataArrayInt::Pow : number of components of both arrays must be equal to 1 !");
8911 MCAuto<DataArrayInt> ret=DataArrayInt::New(); ret->alloc(nbOfTuple,1);
8912 const int *ptr1(a1->begin()),*ptr2(a2->begin());
8913 int *ptr=ret->getPointer();
8914 for(int i=0;i<nbOfTuple;i++,ptr1++,ptr2++,ptr++)
8919 for(int j=0;j<*ptr2;j++)
8925 std::ostringstream oss; oss << "DataArrayInt::Pow : on tuple #" << i << " of a2 value is < 0 (" << *ptr2 << ") !";
8926 throw INTERP_KERNEL::Exception(oss.str().c_str());
8933 * Apply pow on values of another DataArrayInt to values of \a this one.
8935 * \param [in] other - an array to pow to \a this one.
8936 * \throw If \a other is NULL.
8937 * \throw If \a this->getNumberOfTuples() != \a other->getNumberOfTuples()
8938 * \throw If \a this->getNumberOfComponents() != 1 or \a other->getNumberOfComponents() != 1
8939 * \throw If there is a negative value in \a other.
8941 void DataArrayInt::powEqual(const DataArrayInt *other)
8944 throw INTERP_KERNEL::Exception("DataArrayInt::powEqual : input instance is null !");
8945 int nbOfTuple=getNumberOfTuples();
8946 int nbOfTuple2=other->getNumberOfTuples();
8947 int nbOfComp=getNumberOfComponents();
8948 int nbOfComp2=other->getNumberOfComponents();
8949 if(nbOfTuple!=nbOfTuple2)
8950 throw INTERP_KERNEL::Exception("DataArrayInt::powEqual : number of tuples mismatches !");
8951 if(nbOfComp!=1 || nbOfComp2!=1)
8952 throw INTERP_KERNEL::Exception("DataArrayInt::powEqual : number of components of both arrays must be equal to 1 !");
8953 int *ptr=getPointer();
8954 const int *ptrc=other->begin();
8955 for(int i=0;i<nbOfTuple;i++,ptrc++,ptr++)
8960 for(int j=0;j<*ptrc;j++)
8966 std::ostringstream oss; oss << "DataArrayInt::powEqual : on tuple #" << i << " of other value is < 0 (" << *ptrc << ") !";
8967 throw INTERP_KERNEL::Exception(oss.str().c_str());
8974 * Returns a C array which is a renumbering map in "Old to New" mode for the input array.
8975 * This map, if applied to \a start array, would make it sorted. For example, if
8976 * \a start array contents are [9,10,0,6,4,11,3,7] then the contents of the result array is
8977 * [5,6,0,3,2,7,1,4].
8978 * \param [in] start - pointer to the first element of the array for which the
8979 * permutation map is computed.
8980 * \param [in] end - pointer specifying the end of the array \a start, so that
8981 * the last value of \a start is \a end[ -1 ].
8982 * \return int * - the result permutation array that the caller is to delete as it is no
8984 * \throw If there are equal values in the input array.
8986 int *DataArrayInt::CheckAndPreparePermutation(const int *start, const int *end)
8988 std::size_t sz=std::distance(start,end);
8989 int *ret=(int *)malloc(sz*sizeof(int));
8990 int *work=new int[sz];
8991 std::copy(start,end,work);
8992 std::sort(work,work+sz);
8993 if(std::unique(work,work+sz)!=work+sz)
8997 throw INTERP_KERNEL::Exception("Some elements are equals in the specified array !");
8999 std::map<int,int> m;
9000 for(int *workPt=work;workPt!=work+sz;workPt++)
9001 m[*workPt]=(int)std::distance(work,workPt);
9003 for(const int *iter=start;iter!=end;iter++,iter2++)
9010 * Returns a new DataArrayInt containing an arithmetic progression
9011 * that is equal to the sequence returned by Python \c range(\a begin,\a end,\a step )
9013 * \param [in] begin - the start value of the result sequence.
9014 * \param [in] end - limiting value, so that every value of the result array is less than
9016 * \param [in] step - specifies the increment or decrement.
9017 * \return DataArrayInt * - a new instance of DataArrayInt. The caller is to delete this
9018 * array using decrRef() as it is no more needed.
9019 * \throw If \a step == 0.
9020 * \throw If \a end < \a begin && \a step > 0.
9021 * \throw If \a end > \a begin && \a step < 0.
9023 DataArrayInt *DataArrayInt::Range(int begin, int end, int step)
9025 int nbOfTuples=GetNumberOfItemGivenBESRelative(begin,end,step,"DataArrayInt::Range");
9026 MCAuto<DataArrayInt> ret=DataArrayInt::New();
9027 ret->alloc(nbOfTuples,1);
9028 int *ptr=ret->getPointer();
9031 for(int i=begin;i<end;i+=step,ptr++)
9036 for(int i=begin;i>end;i+=step,ptr++)
9043 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
9046 void DataArrayInt::getTinySerializationIntInformation(std::vector<int>& tinyInfo) const
9051 tinyInfo[0]=getNumberOfTuples();
9052 tinyInfo[1]=getNumberOfComponents();
9062 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
9065 void DataArrayInt::getTinySerializationStrInformation(std::vector<std::string>& tinyInfo) const
9069 int nbOfCompo=getNumberOfComponents();
9070 tinyInfo.resize(nbOfCompo+1);
9071 tinyInfo[0]=getName();
9072 for(int i=0;i<nbOfCompo;i++)
9073 tinyInfo[i+1]=getInfoOnComponent(i);
9078 tinyInfo[0]=getName();
9083 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
9084 * This method returns if a feeding is needed.
9086 bool DataArrayInt::resizeForUnserialization(const std::vector<int>& tinyInfoI)
9088 int nbOfTuple=tinyInfoI[0];
9089 int nbOfComp=tinyInfoI[1];
9090 if(nbOfTuple!=-1 || nbOfComp!=-1)
9092 alloc(nbOfTuple,nbOfComp);
9099 * Useless method for end user. Only for MPI/Corba/File serialsation for multi arrays class.
9100 * This method returns if a feeding is needed.
9102 void DataArrayInt::finishUnserialization(const std::vector<int>& tinyInfoI, const std::vector<std::string>& tinyInfoS)
9104 setName(tinyInfoS[0]);
9107 int nbOfCompo=tinyInfoI[1];
9108 for(int i=0;i<nbOfCompo;i++)
9109 setInfoOnComponent(i,tinyInfoS[i+1]);
9113 DataArrayIntIterator::DataArrayIntIterator(DataArrayInt *da):DataArrayIterator<int>(da)
9117 DataArrayIntTuple::DataArrayIntTuple(int *pt, int nbOfComp):DataArrayTuple<int>(pt,nbOfComp)
9121 std::string DataArrayIntTuple::repr() const
9123 std::ostringstream oss; oss << "(";
9124 for(int i=0;i<_nb_of_compo-1;i++)
9125 oss << _pt[i] << ", ";
9126 oss << _pt[_nb_of_compo-1] << ")";
9130 int DataArrayIntTuple::intValue() const
9134 throw INTERP_KERNEL::Exception("DataArrayIntTuple::intValue : DataArrayIntTuple instance has not exactly 1 component -> Not possible to convert it into an integer !");
9138 * This method returns a newly allocated instance the caller should dealed with by a MEDCoupling::DataArrayInt::decrRef.
9139 * This method performs \b no copy of data. The content is only referenced using MEDCoupling::DataArrayInt::useArray with ownership set to \b false.
9140 * 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
9141 * \b nbOfCompo=1 and \bnbOfTuples==this->_nb_of_elem.
9143 DataArrayInt *DataArrayIntTuple::buildDAInt(int nbOfTuples, int nbOfCompo) const
9145 if((_nb_of_compo==nbOfCompo && nbOfTuples==1) || (_nb_of_compo==nbOfTuples && nbOfCompo==1))
9147 DataArrayInt *ret=DataArrayInt::New();
9148 ret->useExternalArrayWithRWAccess(_pt,nbOfTuples,nbOfCompo);
9153 std::ostringstream oss; oss << "DataArrayIntTuple::buildDAInt : unable to build a requested DataArrayInt instance with nbofTuple=" << nbOfTuples << " and nbOfCompo=" << nbOfCompo;
9154 oss << ".\nBecause the number of elements in this is " << _nb_of_compo << " !";
9155 throw INTERP_KERNEL::Exception(oss.str().c_str());