+ /*!
+ * Elements of \a partOfThis are expected to be included in \a this.
+ * The returned array \a ret is so that this[ret]==partOfThis
+ *
+ * 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]
+ * the return array will contain [3,2,5,7].
+ *
+ * \a this is expected to be a 1 compo allocated array.
+ * \param [in] partOfThis - A 1 compo allocated array
+ * \return - A newly allocated array to be dealed by caller having the same number of tuples than \a partOfThis.
+ * \throw if two same element is present twice in \a this
+ * \throw if an element in \a partOfThis is \b NOT in \a this.
+ */
+ template<class T>
+ DataArrayIdType *DataArrayDiscrete<T>::indicesOfSubPart(const DataArrayDiscrete<T>& partOfThis) const
+ {
+ if(this->getNumberOfComponents()!=1 || partOfThis.getNumberOfComponents()!=1)
+ throw INTERP_KERNEL::Exception("DataArrayInt::indicesOfSubPart : this and input array must be one component array !");
+ this->checkAllocated(); partOfThis.checkAllocated();
+ std::size_t thisNbTuples(this->getNumberOfTuples()),nbTuples(partOfThis.getNumberOfTuples());
+ const T *thisPt(this->begin()),*pt(partOfThis.begin());
+ MCAuto<DataArrayIdType> ret(DataArrayIdType::New());
+ ret->alloc(nbTuples,1);
+ T *retPt(ret->getPointer());
+ std::map<int,mcIdType> m;
+ for(std::size_t i=0;i<thisNbTuples;i++,thisPt++)
+ m[*thisPt]=(mcIdType)i;
+ if(m.size()!=thisNbTuples)
+ throw INTERP_KERNEL::Exception("DataArrayInt::indicesOfSubPart : some elements appears more than once !");
+ for(std::size_t i=0;i<nbTuples;i++,retPt++,pt++)
+ {
+ std::map<int,mcIdType>::const_iterator it(m.find(*pt));
+ if(it!=m.end())
+ *retPt=(*it).second;
+ else
+ {
+ std::ostringstream oss; oss << "DataArrayInt::indicesOfSubPart : At pos #" << i << " of input array value is " << *pt << " not in this !";
+ throw INTERP_KERNEL::Exception(oss.str());
+ }
+ }
+ return ret.retn();
+ }
+
+ /*!
+ * Checks that \a this array is consistently **increasing** or **decreasing** in value.
+ * If not an exception is thrown.
+ * \param [in] increasing - if \a true, the array values should be increasing.
+ * \throw If sequence of values is not strictly monotonic in agreement with \a
+ * increasing arg.
+ * \throw If \a this->getNumberOfComponents() != 1.
+ * \throw If \a this is not allocated.
+ */
+ template<class T>
+ void DataArrayDiscrete<T>::checkMonotonic(bool increasing) const
+ {
+ if(!isMonotonic(increasing))
+ {
+ if (increasing)
+ throw INTERP_KERNEL::Exception("DataArrayInt::checkMonotonic : 'this' is not INCREASING monotonic !");
+ else
+ throw INTERP_KERNEL::Exception("DataArrayInt::checkMonotonic : 'this' is not DECREASING monotonic !");
+ }
+ }
+
+ /*!
+ * Checks that \a this array is consistently **increasing** or **decreasing** in value.
+ * \param [in] increasing - if \a true, array values should be increasing.
+ * \return bool - \a true if values change in accordance with \a increasing arg.
+ * \throw If \a this->getNumberOfComponents() != 1.
+ * \throw If \a this is not allocated.
+ */
+ template<class T>
+ bool DataArrayDiscrete<T>::isMonotonic(bool increasing) const
+ {
+ this->checkAllocated();
+ if(this->getNumberOfComponents()!=1)
+ throw INTERP_KERNEL::Exception("DataArrayInt::isMonotonic : only supported with 'this' array with ONE component !");
+ std::size_t nbOfElements(this->getNumberOfTuples());
+ const T *ptr(this->begin());
+ if(nbOfElements==0)
+ return true;
+ T ref(ptr[0]);
+ if(increasing)
+ {
+ for(std::size_t i=1;i<nbOfElements;i++)
+ {
+ if(ptr[i]>=ref)
+ ref=ptr[i];
+ else
+ return false;
+ }
+ }
+ else
+ {
+ for(std::size_t i=1;i<nbOfElements;i++)
+ {
+ if(ptr[i]<=ref)
+ ref=ptr[i];
+ else
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /*!
+ * This method check that array consistently INCREASING or DECREASING in value.
+ */
+ template<class T>
+ bool DataArrayDiscrete<T>::isStrictlyMonotonic(bool increasing) const
+ {
+ this->checkAllocated();
+ if(this->getNumberOfComponents()!=1)
+ throw INTERP_KERNEL::Exception("DataArrayInt::isStrictlyMonotonic : only supported with 'this' array with ONE component !");
+ std::size_t nbOfElements(this->getNumberOfTuples());
+ const T *ptr(this->begin());
+ if(nbOfElements==0)
+ return true;
+ T ref(ptr[0]);
+ if(increasing)
+ {
+ for(std::size_t i=1;i<nbOfElements;i++)
+ {
+ if(ptr[i]>ref)
+ ref=ptr[i];
+ else
+ return false;
+ }
+ }
+ else
+ {
+ for(std::size_t i=1;i<nbOfElements;i++)
+ {
+ if(ptr[i]<ref)
+ ref=ptr[i];
+ else
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /*!
+ * This method check that array consistently INCREASING or DECREASING in value.
+ */
+ template<class T>
+ void DataArrayDiscrete<T>::checkStrictlyMonotonic(bool increasing) const
+ {
+ if(!isStrictlyMonotonic(increasing))
+ {
+ if (increasing)
+ throw INTERP_KERNEL::Exception("DataArrayInt::checkStrictlyMonotonic : 'this' is not strictly INCREASING monotonic !");
+ else
+ throw INTERP_KERNEL::Exception("DataArrayInt::checkStrictlyMonotonic : 'this' is not strictly DECREASING monotonic !");
+ }
+ }
+
+ ////////////////////////////////////
+