ML Reference
MeVis/Foundation/Sources/MLLinearAlgebra/mlIntegerVector.h
Go to the documentation of this file.
00001 // **InsertLicense** code 
00002 //-------------------------------------------------------------------------
00004 
00009 //-------------------------------------------------------------------------
00010 #ifndef __mlIntegerVector_H
00011 #define __mlIntegerVector_H
00012 
00013 // ML-includes
00014 #ifndef __mlLinearAlgebra_H
00015 #include "mlLinearAlgebra.h"
00016 #endif
00017 
00018 
00019 ML_START_NAMESPACE
00020 
00021   //-------------------------------------------------------------------------
00023   //-------------------------------------------------------------------------
00024   typedef int VectorDimIdxType;
00025 
00026   //-------------------------------------------------------------------------
00032   //-------------------------------------------------------------------------
00033   template <typename CompIntType, VectorDimIdxType NumDim> 
00034   class TVectorNDBase 
00035   {
00036     public:
00037 
00039     typedef CompIntType ComponentType;
00040 
00042     enum { NumberOfDimensions = NumDim };
00043 
00046     ComponentType array[NumberOfDimensions];
00047 
00048     protected:
00049     
00053     TVectorNDBase(){};
00054   };
00055 
00056   //-------------------------------------------------------------------------
00060 
00104   //-------------------------------------------------------------------------
00105   template<class TVectorBase> 
00106   class TVector : public TVectorBase 
00107   {
00108   public:
00109 
00111     typedef typename TVectorBase::ComponentType ComponentType;
00112 
00114     typedef TVectorBase ParentClass;
00115 
00117     enum { NumberOfDimensions = ParentClass::NumberOfDimensions };
00118 
00119 
00120     //------------------------------------------------------
00122 
00123     //------------------------------------------------------
00125     inline TVector() : ParentClass()
00126     {
00127       ML_TRACE_IN_TIME_CRITICAL( "TVector( )" );
00128       memset(this->array, 0, static_cast<size_t>(NumberOfDimensions)*sizeof(ComponentType));
00129     }
00130   
00132     inline explicit TVector(const ComponentType i) : ParentClass()
00133     {
00134       ML_TRACE_IN_TIME_CRITICAL( "TVector(const ComponentType i)" );
00135       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d]=i; }
00136     }
00137   
00139     inline TVector(const TVector<TVectorBase> &v2) : ParentClass()
00140     {
00141       ML_TRACE_IN_TIME_CRITICAL( "TVector(const TVector<TVectorBase> &v2)" );
00142       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d]=v2.array[d]; }
00143     }
00144   
00147     template <typename TVectorBase2>
00148     inline explicit TVector(const TVector<TVectorBase2> &v2) : ParentClass()
00149     {
00150       ML_TRACE_IN_TIME_CRITICAL( "TVector(const TVector<T2, TVectorBase > &v2)" );
00151       VectorDimIdxType numDims = NumberOfDimensions;
00152       if (v2.NumberOfDimensions < numDims){ numDims = v2.NumberOfDimensions; }
00153       VectorDimIdxType d=0;
00154       for (; d < numDims; ++d){
00155         this->array[d] = static_cast<ComponentType>(v2.array[d]);
00156       }
00157       for (; d < NumberOfDimensions; ++d){
00158         this->array[d] = 0;
00159       }
00160     }
00161     
00163     inline explicit TVector(const ComponentType xp, const TVector &p) : ParentClass()
00164     {
00165       ML_TRACE_IN_TIME_CRITICAL( "TVector(const ComponentType xp, const TVector &p)" );
00166       this->array[0] = xp;
00167       for (VectorDimIdxType d=1; d < NumberOfDimensions; ++d){ this->array[d] = p.array[d]; }
00168     }
00169 
00173     inline explicit TVector(const MLint num, const ComponentType* const arr, const ComponentType deflt);
00174   
00179     inline void copy(const MLint num, ComponentType* const arr) const;
00180 
00182     inline void set(const ComponentType v=0)
00183     { 
00184       ML_TRACE_IN_TIME_CRITICAL("TVector::set(const ComponentType v=0)");
00185       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d]=v; } 
00186     }
00187 
00189     inline void set(const TVector &v)
00190     { 
00191       ML_TRACE_IN_TIME_CRITICAL("TVector::set(const TVector &v)");
00192       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] = v.array[d]; }
00193     }
00195 
00196 
00197     //------------------------------------------------------
00199 
00200     //------------------------------------------------------
00201 
00203     inline TVector<TVectorBase>  operator+ (const TVector &b) const 
00204     { 
00205       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator + " );
00206       return TVector<TVectorBase>(*this) += b;
00207     }
00209     inline TVector<TVectorBase> &operator+= (const TVector<TVectorBase> &b)       
00210     { 
00211       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator += " );
00212       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] += b.array[d]; }
00213       return *this;
00214     }
00216     inline TVector<TVectorBase>  operator- (const TVector<TVectorBase> &b) const 
00217     { 
00218       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator - " );
00219       return TVector<TVectorBase>(*this) -= b;
00220     }
00222     inline TVector<TVectorBase> &operator-= (const TVector<TVectorBase> &b)       
00223     { 
00224       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator -= " );
00225       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] -= b.array[d]; }
00226       return *this;
00227     }
00229     inline TVector<TVectorBase>  operator* (const TVector<TVectorBase> &b) const 
00230     { 
00231       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator * " );
00232       return TVector<TVectorBase>(*this) *= b;
00233     }
00235     inline TVector<TVectorBase> &operator*= (const TVector<TVectorBase> &b)       
00236     { 
00237       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator *= " );
00238       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] *= b.array[d]; }
00239       return *this;
00240     }
00242     inline TVector<TVectorBase>  operator+ (const ComponentType b) const 
00243     { 
00244       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator + " );
00245       TVector<TVectorBase> retVec(*this);
00246       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ retVec.array[d] += b; }
00247       return retVec;
00248     }
00250     inline TVector<TVectorBase>  operator- (const ComponentType b) const 
00251     { 
00252       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator - " );
00253       TVector<TVectorBase> retVec(*this);
00254       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ retVec.array[d] -= b; }
00255       return retVec;
00256     }
00258     inline TVector<TVectorBase>  operator* (const ComponentType b) const 
00259     { 
00260       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator * " );
00261       TVector<TVectorBase> retVec(*this);
00262       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ retVec.array[d] *= b; }
00263       return retVec;
00264     }
00266     inline TVector<TVectorBase>  operator/ (const TVector<TVectorBase> &b) const 
00267     {
00268       ML_TRACE_IN( "TVector::operator / " );
00269       return TVector<TVectorBase>(*this) /= b;
00270     }
00272     inline TVector<TVectorBase> &operator/= (const TVector<TVectorBase> &b) 
00273     {
00274       ML_TRACE_IN( "TVector::operator /= " );
00275       ML_TRY
00276       {
00277         for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ 
00278           ML_CHECK_THROW(b.array[d]); 
00279           this->array[d] /= b.array[d];
00280         }
00281       }
00282       ML_CATCH_RETHROW;
00283       return *this;
00284     }
00287     inline bool operator== (const TVector<TVectorBase> &b) const 
00288     { 
00289       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator == " );
00290       bool retFlag = true;
00291       for (VectorDimIdxType d=0; retFlag && (d < NumberOfDimensions); ++d){ retFlag &= (this->array[d] == b.array[d]); }
00292       return retFlag;
00293     }
00296     inline bool operator!= (const TVector<TVectorBase> &b) const 
00297     { 
00298       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator != " );
00299       return !(*this == b);
00300     }
00301 
00303     inline bool operator< (const TVector<TVectorBase> &b) const 
00304     { 
00305       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator < " );
00306       bool retFlag = true;
00307       for (VectorDimIdxType d=0; retFlag && (d < NumberOfDimensions); ++d){ retFlag &= (this->array[d] < b.array[d]); }
00308       return retFlag;
00309     }
00311     inline bool operator<= (const TVector<TVectorBase> &b) const 
00312     { 
00313       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator <= " );
00314       bool retFlag = true;
00315       for (VectorDimIdxType d=0; retFlag && (d < NumberOfDimensions); ++d){ retFlag &= (this->array[d] <= b.array[d]); }
00316       return retFlag;
00317     }
00319     inline bool operator> (const TVector<TVectorBase> &b) const 
00320     { 
00321       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator > " );
00322       bool retFlag = true;
00323       for (VectorDimIdxType d=0; retFlag && (d < NumberOfDimensions); ++d){ retFlag &= (this->array[d] > b.array[d]); }
00324       return retFlag;
00325     }
00327     inline bool operator>= (const TVector<TVectorBase> &b) const 
00328     { 
00329       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator >= " );
00330       bool retFlag = true;
00331       for (VectorDimIdxType d=0; retFlag && (d < NumberOfDimensions); ++d){ retFlag &= (this->array[d] >= b.array[d]); }
00332       return retFlag;
00333     }
00334 
00336     inline TVector<TVectorBase>  operator& (const TVector<TVectorBase> &b) const 
00337     { 
00338       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator & " );
00339       return TVector<TVectorBase>(*this) &= b;
00340     }
00342     inline TVector<TVectorBase>  operator| (const TVector<TVectorBase> &b) const 
00343     { 
00344       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator | " );
00345       return TVector<TVectorBase>(*this) |= b;
00346     }
00348     inline TVector<TVectorBase>  operator^  (const TVector<TVectorBase> &b) const 
00349     { 
00350       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator ^ " );
00351       return TVector<TVectorBase>(*this) ^= b;
00352     }
00353 
00355     inline TVector<TVectorBase> &operator &= (const TVector<TVectorBase> &b)       
00356     { 
00357       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator &= " );
00358       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] &= b.array[d]; }
00359       return *this; 
00360     }
00362     inline TVector<TVectorBase> &operator |= (const TVector<TVectorBase> &b)       
00363     { 
00364       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator |= " );
00365       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] |= b.array[d]; }
00366       return *this; 
00367     }
00369     inline TVector<TVectorBase> &operator ^= (const TVector<TVectorBase> &b)       
00370     { 
00371       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator ^= " );
00372       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] ^= b.array[d]; }
00373       return *this; 
00374     }
00375 
00377     inline TVector<TVectorBase>  operator& (const ComponentType b) const 
00378     { 
00379       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator & " );
00380       return TVector<TVectorBase>(*this) &= b;
00381     }
00383     inline TVector<TVectorBase>  operator| (const ComponentType b) const 
00384     { 
00385       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator | " );
00386       return TVector<TVectorBase>(*this) |= b;
00387     }
00389     inline TVector<TVectorBase>  operator^ (const ComponentType b) const 
00390     { 
00391       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator ^ " );
00392       return TVector<TVectorBase>(*this) ^= b;
00393     }
00394 
00396     inline TVector<TVectorBase> &operator&= (const ComponentType b)                 
00397     { 
00398       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator &= " );
00399       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] &= b; }
00400       return *this; 
00401     }
00403     inline TVector<TVectorBase> &operator|= (const ComponentType b)                 
00404     { 
00405       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator |= " );
00406       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] |= b; }
00407       return *this; 
00408     }
00410     inline TVector<TVectorBase> &operator^= (const ComponentType b)                 
00411     { 
00412       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator ^= " );
00413       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] ^= b; }
00414       return *this; 
00415     }
00416 
00418     inline TVector<TVectorBase>  operator>> (const int b) const 
00419     { 
00420       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator >> " );
00421       return TVector<TVectorBase>(*this) >>= b;
00422     }
00424     inline TVector<TVectorBase>  operator<< (const int b) const 
00425     { 
00426       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator << " );
00427       return TVector<TVectorBase>(*this) <<= b;
00428     }
00429 
00431     inline TVector<TVectorBase> &operator>>= (const int b)                
00432     { 
00433       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator >>= " );
00434       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] >>= b; }
00435       return *this; 
00436     }
00438     inline TVector<TVectorBase> &operator<<= (const int b)                
00439     { 
00440       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator <<= " );
00441       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] <<= b; }
00442       return *this; 
00443     }
00444 
00446     inline TVector<TVectorBase>  operator- () const 
00447     { 
00448       ML_TRACE_IN_TIME_CRITICAL( "TVector::operator - " );
00449       TVector<TVectorBase> retVec(*this);
00450       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ retVec.array[d] = -retVec.array[d]; }
00451       return retVec;
00452     }
00453 
00457     // Note: No tracing! No try, No catch! Do nothing here which could degrade performance!
00458     inline ComponentType operator[](const size_t i) const { return this->array[i]; }
00459 
00463     // Note: No tracing! No try, No catch! Do nothing here which could degrade performance!
00464     inline ComponentType &operator[](const size_t i)      { return this->array[i]; }
00465 
00467     inline MLint getMaxIdx() const 
00468     {
00469       ML_TRACE_IN_TIME_CRITICAL( "TVector::getMaxIdx()" );
00470       VectorDimIdxType idx = NumberOfDimensions-1; 
00471       ComponentType      val = this->array[idx];
00472       for (VectorDimIdxType d=NumberOfDimensions-2; d >=0; d--){ 
00473         if (this->array[d] >= val){ idx=d; val=this->array[d]; } 
00474       }
00475       return idx;
00476     }
00477 
00479     inline ComponentType getMax() const 
00480     {
00481       ML_TRACE_IN_TIME_CRITICAL( "TVector::getMax()" );
00482       return this->array[getMaxIdx()];
00483     }
00484 
00486     inline MLint getMinIdx() const 
00487     { 
00488       ML_TRACE_IN_TIME_CRITICAL( "TVector::getMinIdx()" );
00489       VectorDimIdxType idx = NumberOfDimensions-1; 
00490       ComponentType      val = this->array[idx];
00491       for (VectorDimIdxType d=NumberOfDimensions-2; d >= 0; d--){ 
00492         if (this->array[d] <= val){ idx=d; val=this->array[d]; }
00493       }
00494       return idx;
00495     }
00496 
00498     inline ComponentType getMin() const 
00499     { 
00500       ML_TRACE_IN_TIME_CRITICAL( "TVector::getMin()" );
00501       return this->array[getMinIdx()];
00502     }
00503 
00509     inline TVector<TVectorBase> getStrides(const ComponentType offset=1) const;
00510 
00516     inline TVector<TVectorBase> getVectorPosition(ComponentType offsetPos) const;
00517 
00520     inline MLint getExtDimension() const;
00521 
00523     inline bool hasNegativeComp() const 
00524     {
00525       ML_TRACE_IN_TIME_CRITICAL( "TVector::hasNegativeComp()" );
00526       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ if (this->array[d]<0){ return true; } }
00527       return false; 
00528     }
00529 
00531     inline bool allBiggerZero() const
00532     { 
00533       ML_TRACE_IN_TIME_CRITICAL( "TVector::allBiggerZero()" );
00534       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ if (this->array[d]<=0){ return false; } }
00535       return true; 
00536     }
00538 
00539 
00540     //------------------------------------------------------
00542 
00543     //------------------------------------------------------
00544     // Methods:
00547     inline TVector<TVectorBase> divCeil(const TVector<TVectorBase> &b) const { return TVector<TVectorBase>::divCeil(*this, b); }
00549     inline TVector<TVectorBase> compMin(const TVector<TVectorBase> &b) const { return TVector<TVectorBase>::compMin(*this, b); }
00551     inline TVector<TVectorBase> compMax(const TVector<TVectorBase> &b) const { return TVector<TVectorBase>::compMax(*this, b); }
00554     inline TVector<TVectorBase> compMod(const TVector<TVectorBase> &b) const { return TVector<TVectorBase>::compMod(*this, b); }
00556     inline TVector<TVectorBase> compAbs()                              const { return TVector<TVectorBase>::compAbs(*this);    }
00557 
00559     inline ComponentType          compMul()                              const { return TVector<TVectorBase>::compMul(*this);    }
00561     inline ComponentType          compSum()                              const { return TVector<TVectorBase>::compSum(*this);    }
00562 
00564     inline ComponentType          dot(const TVector<TVectorBase> &b)     const { return TVector<TVectorBase>::dot(*this, b);     }
00565 
00568     static TVector<TVectorBase> divCeil(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b);
00570     static TVector<TVectorBase> compMin(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b);
00572     static TVector<TVectorBase> compMax(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b);
00575     static TVector<TVectorBase> compMod(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b);
00577     static TVector<TVectorBase> compAbs(const TVector<TVectorBase> &a);
00578 
00580     inline static ComponentType   compMul(const TVector<TVectorBase> &a) 
00581     { 
00582       ML_TRACE_IN_TIME_CRITICAL( "TVector::compMul()" );
00583       ComponentType retVal = a.array[0];
00584       for (VectorDimIdxType d=1; d < NumberOfDimensions; ++d){ retVal *= a.array[d]; }
00585       return retVal;
00586     }
00588     inline static ComponentType   compSum(const TVector<TVectorBase> &a) 
00589     { 
00590       ML_TRACE_IN_TIME_CRITICAL( "TVector::compSum()" );
00591       ComponentType retVal = a.array[0];
00592       for (VectorDimIdxType d=1; d < NumberOfDimensions; ++d){ retVal += a.array[d]; }
00593       return retVal;
00594     }
00595 
00596 
00598     inline static ComponentType dot(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b) 
00599     { 
00600       ML_TRACE_IN_TIME_CRITICAL( "TVector::dot()" );
00601       ComponentType retVal = a.array[0]*b.array[0];
00602       for (VectorDimIdxType d=1; d < NumberOfDimensions; ++d){ retVal += a.array[d]*b.array[d]; }
00603       return retVal;
00604     }
00605 
00607     inline void fillSmallerComps(const ComponentType threshold=0, const ComponentType fillVal=0) 
00608     { 
00609       ML_TRACE_IN_TIME_CRITICAL( "TVector::fillSmallerComps()" );
00610       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ if (this->array[d] < threshold){ this->array[d] = fillVal; } }
00611     }
00612 
00614     inline void fillGreaterComps(const ComponentType threshold=0, const ComponentType fillVal=0) 
00615     { 
00616       ML_TRACE_IN_TIME_CRITICAL( "TVector::fillGreaterComps()" );
00617       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ if (this->array[d] > threshold){ this->array[d] = fillVal; } }
00618     }
00619 
00621     inline void fillEqualComps(const ComponentType threshold=0, const ComponentType fillVal=0) 
00622     { 
00623       ML_TRACE_IN_TIME_CRITICAL( "TVector::fillEqualComps()" );
00624       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ if (this->array[d] == threshold){ this->array[d] = fillVal; } }
00625     }
00627 
00631     std::string print(const std::string &openStr="",
00632                       const std::string &sepStr=" ",
00633                       const std::string &termStr="",
00634                       const MLint16 numDigits=-1) const;
00635 
00636   };
00637 
00638 ML_END_NAMESPACE
00639 
00640 
00641 //-----------------------------------------------------------------------------------
00642 //   Stream output for std::ostream
00643 //-----------------------------------------------------------------------------------
00644 namespace std {
00645 
00648   template <class TVectorBase>
00649   inline ostream& operator<<(ostream& s, const ML_NAMESPACE::TVector<TVectorBase> &v){
00650     s << "(";
00651     for (ML_NAMESPACE::VectorDimIdxType d=0; d < ML_NAMESPACE::TVector<TVectorBase>::NumberOfDimensions-1; ++d){ s << v.array[d] << ","; }
00652     s << v.array[ML_NAMESPACE::TVector<TVectorBase>::NumberOfDimensions-1];
00653     s << ")";
00654     return s;
00655   };
00656 
00657 }
00658 
00659 
00660 
00661 ML_START_NAMESPACE
00662 
00663 
00664   //------------------------------------------------------
00665   //            TVector<TVectorBase>       
00666   //------------------------------------------------------
00667   // Constructor which initializes the vector components by copying them from
00668   // arr[0] ,..., arr[num-1]. All other elements are initialized to
00669   // the value deflt.
00670   template <class TVectorBase>
00671   inline TVector<TVectorBase>::TVector(const MLint num, const ComponentType* const arr, const ComponentType deflt) : ParentClass()
00672   {
00673     ML_TRACE_IN( "TVector<TVectorBase>::TVector" );
00674     ML_TRY
00675     {      
00676       ML_CHECK_THROW(arr);
00677       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ this->array[d] = (num>d ? arr[d] : deflt); }
00678     }
00679     ML_CATCH_RETHROW;
00680   }
00681 
00682   // Copy the first num elements from internal array into arr
00683   // starting with array[0] to arr[0] to array[num-1] to arr[num-1], respectively.
00684   // All other components are left unchanged.
00685   // arr must have at least num entries and at most NumberOfDimensions elements are copied.
00686   template <class TVectorBase>
00687   inline void TVector<TVectorBase>::copy(const MLint num, ComponentType* const arr) const
00688   {
00689     ML_TRACE_IN( "TVector<TVectorBase>::copy" );
00690     ML_TRY
00691     {
00692       ML_CHECK_THROW(arr);
00693       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ if (num>d){ arr[d] = this->array[d]; } }
00694     }
00695     ML_CATCH_RETHROW;
00696   }
00697 
00698   // Interprets vector as image extent and returns a stride vector.
00699   // The smallest stride (the x stride) is set to offset, i.e. an
00700   // image voxel is assumed to have size = offset.
00701   // So stride.x = offset, stride.y = offset*x, stride.z = offset*x*y, ...,
00702   // stride.u=offset*x*y*z*c*t.
00703   template <class TVectorBase>
00704   inline TVector<TVectorBase> TVector<TVectorBase>::getStrides(const ComponentType offset) const
00705   {
00706     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::getStrides" );
00707     TVector<TVectorBase> stride;
00708     stride.array[0] = offset;
00709     for (VectorDimIdxType d=1; d < NumberOfDimensions; ++d){ stride.array[d] = stride.array[d-1] * this->array[d-1]; }
00710     return stride;
00711   }
00712 
00713   // Interprets the vector as a stride vector of an image and returns the offset
00714   // position offsetPos from the image origin to the coordinate specified by
00715   // the vector. For offsetPos, an image with extents given by *this and the return
00716   // value rv then holds:
00717   // \code offsetPos = rv.x*x + rv.y*y + ... + rv.u*u \endcode )
00718   template <class TVectorBase>
00719   inline TVector<TVectorBase> TVector<TVectorBase>::getVectorPosition(ComponentType offsetPos) const
00720   {
00721     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::getVectorPosition" );
00722       
00723     TVector<TVectorBase> vectorPos;
00724     
00725     ML_TRY
00726     {
00727       for (VectorDimIdxType d=NumberOfDimensions-1; d>=1; d--){ 
00728         ML_CHECK_THROW(this->array[d]);
00729         vectorPos.array[d] = offsetPos / this->array[d];
00730         offsetPos = offsetPos % this->array[d];
00731       }
00732       ML_CHECK_THROW(this->array[0]);
00733       vectorPos.array[0] = offsetPos / this->array[0];
00734     }
00735     ML_CATCH_RETHROW;
00736     
00737     return vectorPos;
00738   }
00739 
00740   // Returns the highest vector component which is not 1. Useful to get the real dimension of an image.
00741   template <class TVectorBase>
00742   inline MLint TVector<TVectorBase>::getExtDimension() const
00743   {
00744     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::getExtDimension()" );
00745       
00746     VectorDimIdxType dimen = 1;
00747     for (VectorDimIdxType d=NumberOfDimensions-1; d >=1; d--){ 
00748       if (1 != this->array[d]){ 
00749         dimen = d+1;
00750         break;
00751       }
00752     }
00753     return dimen;
00754   }
00755 
00756   // Return the componentwise division of the vector this by vector b with rounding up.
00757   // Division by zero caused by zero components of b must be avoided by caller.
00758   template <class TVectorBase>
00759   inline TVector<TVectorBase> TVector<TVectorBase>::divCeil(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b)
00760   {
00761     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::divCeil" );
00762       
00763     TVector<TVectorBase> c;
00764     
00765     ML_TRY
00766     {
00767       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ 
00768         ML_CHECK_THROW(b.array[d]);
00769         c.array[d] = static_cast<ComponentType>(ceil(static_cast<MLdouble>(a.array[d])/b.array[d]));
00770       }
00771     }
00772     ML_CATCH_RETHROW;    
00773     return c;
00774   }
00775 
00776 
00777   // Return the componentwise minimum of TVector<TVectorBase>s this and b.
00778   template <class TVectorBase>
00779   inline TVector<TVectorBase> TVector<TVectorBase>::compMin(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b)
00780   {
00781     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::compMin" );
00782       
00783     TVector<TVectorBase> c(b);
00784     for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ 
00785       if (a.array[d] < c.array[d]){ c.array[d] = a.array[d]; }
00786     }
00787     return c;
00788   }
00789 
00790   // Return the componentwise maximum of vectors this and b.
00791   template <class TVectorBase>
00792   inline TVector<TVectorBase> TVector<TVectorBase>::compMax(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b)
00793   {
00794     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::compMax" );
00795       
00796     TVector<TVectorBase> c(b);
00797     for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ 
00798       if (a.array[d] > c.array[d]){ c.array[d] = a.array[d]; }
00799     }
00800     return c;
00801   }
00802 
00803   // Return the rest dividing vector this a by b componentwise.
00804   // Division by zero caused by zero components of b must be avoided by caller and will 
00805   // be handled as fatal error exception otherwise.
00806   template <class TVectorBase>
00807   inline TVector<TVectorBase> TVector<TVectorBase>::compMod(const TVector<TVectorBase> &a, const TVector<TVectorBase> &b)
00808   {
00809     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::compMod" );
00810       
00811     TVector<TVectorBase> c;
00812     ML_TRY
00813     {
00814       for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ 
00815         ML_CHECK_THROW(b.array[d]);
00816         c.array[d] = a.array[d] % b.array[d];
00817       }
00818     }
00819     ML_CATCH_RETHROW;
00820     return c;
00821   }
00822 
00823   // Return a vector with all components of a replaced by their absolute values.
00824   template <class TVectorBase>
00825   inline TVector<TVectorBase> TVector<TVectorBase>::compAbs(const TVector<TVectorBase> &a) 
00826   {
00827     ML_TRACE_IN_TIME_CRITICAL( "TVector<TVectorBase>::compAbs" );
00828       
00829     TVector<TVectorBase> c(a);
00830     for (VectorDimIdxType d=0; d < NumberOfDimensions; ++d){ 
00831       if (c.array[d]<0){ c.array[d] = -c.array[d]; }
00832     }
00833     return c;
00834   }
00835 
00836   // Returns the string openStr + v.x + sepStr + ... + v.t + sepStr + v.u + termStr.
00837   // numDigits is the number of digits to be used as print parameter.
00838   // If numDigits is <=0 then no space specification is used.
00839   template <class TVectorBase>
00840   inline std::string TVector<TVectorBase>::print(const std::string &openStr,
00841                                                  const std::string &sepStr,
00842                                                  const std::string &termStr,
00843                                                  const MLint16      numDigits) const
00844   {
00845     ML_TRACE_IN( "TVector<TVectorBase>::print" );
00846 
00847     std::string result = openStr;
00848     ML_TRY
00849     {
00850       // 512 chars are sufficient, because MLint64 or even in future MLint 
00851       // as 128 bit version does not use more than 2^128 digits which are 
00852       // about 10^43.
00853       char buf [512]="";
00854       char frmt[100]="";
00855 
00856       // Create a format string with or without space specifications 
00857       // dependent on numDigits.
00858       if (numDigits>=0){
00859         MLsnprintf(frmt, 99, "%%%dI64Ld", numDigits);
00860       }
00861       else{
00862         MLsnprintf(frmt, 99, "%%I64Ld");
00863       }
00864 
00865       // Print all vector components with platform independent MLsnprintf, 
00866       // because MLint64 prints are needed and 64 bit integer print is 
00867       // platform dependent.
00868       for (VectorDimIdxType d=0; d < NumberOfDimensions-1; ++d){ 
00869         MLsnprintf(buf, 511, frmt, this->array[d]); 
00870         result += buf + sepStr;
00871       }
00872       MLsnprintf(buf, 511, frmt, this->array[NumberOfDimensions-1]); 
00873       result += buf + termStr;
00874     }
00875     ML_CATCH_RETHROW;
00876     return result;
00877   }
00878 
00879 ML_END_NAMESPACE
00880 
00881 #endif //of __mlIntegerVector_H
00882 
00883