Go to the documentation of this file.00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 
00032 
00033 #ifndef __cmtkFixedVector_h_included_
00034 #define __cmtkFixedVector_h_included_
00035 
00036 #include <cmtkconfig.h>
00037 
00038 #include <System/cmtkSmartPtr.h>
00039 #include <System/cmtkSmartConstPtr.h>
00040 
00041 #include <algorithm>
00042 #include <fstream>
00043 
00044 namespace
00045 cmtk
00046 {
00048 template<size_t NDIM,typename T=int>
00049 class FixedVector
00050 {
00051 public:
00053   typedef FixedVector<NDIM,T> Self;
00054 
00056   typedef T ValueType;
00057 
00059   typedef SmartPointer<Self> SmartPtr;
00060 
00062   typedef SmartConstPointer<Self> SmartConstPtr;
00063 
00065   static const Self Zero()
00066   {
00067     Self v;
00068     std::fill( v.begin(), v.end(), 0 );
00069     return v;
00070   }
00071 
00073   FixedVector() {}
00074 
00076   class Init
00077   {
00078   public:
00080     explicit Init( const T value ) : m_Value( value ) {}
00081     
00083     T m_Value;
00084   };
00085   
00087   explicit FixedVector( const typename Self::Init& init )
00088   {
00089     std::fill( this->begin(), this->end(), init.m_Value );
00090   }
00091 
00093   template<class T2>
00094   explicit FixedVector( const T2 *const ptr ) 
00095   { 
00096     for ( size_t i = 0; i < NDIM; ++i )
00097       this->m_Data[i] = ptr[i];
00098   }
00099 
00101   template<class T2>
00102   FixedVector( const FixedVector<NDIM,T2>& rhs )
00103   {
00104     for ( size_t i = 0; i < NDIM; ++i )
00105       this->m_Data[i] = rhs[i];
00106   }
00107 
00109   T& operator[]( const size_t i )
00110   {
00111     return this->m_Data[i];
00112   }
00113 
00115   const T& operator[]( const size_t i ) const
00116   {
00117     return this->m_Data[i];
00118   }
00119 
00121   Self& operator+=( const Self& rhs )
00122   {
00123     for ( size_t i = 0; i<NDIM; ++i )
00124       this->m_Data[i] += rhs.m_Data[i];
00125     return *this;
00126   }
00127   
00129   Self& operator-=( const Self& rhs )
00130   {
00131     for ( size_t i = 0; i<NDIM; ++i )
00132       this->m_Data[i] -= rhs.m_Data[i];
00133     return *this;
00134   }
00135 
00137   bool operator==( const Self& rhs ) const
00138   {
00139     for ( size_t i = 0; i<NDIM; ++i )
00140       if ( this->m_Data[i] != rhs.m_Data[i] )
00141         return false;
00142     return true;
00143   }
00144 
00146   Self& operator*= ( const T a ) 
00147   {
00148     for ( size_t i=0; i<NDIM; ++i ) 
00149       this->m_Data[i] *= a;
00150     return *this;
00151   }
00152   
00154   Self& operator*=( const Self& rhs )
00155   {
00156     for ( size_t i=0; i<NDIM; ++i ) 
00157       this->m_Data[i] *= rhs[i];
00158     return *this;
00159   }
00160 
00162   Self& operator/= ( const T a ) 
00163   {
00164     for ( size_t i=0; i<NDIM; ++i ) 
00165       this->m_Data[i] /= a;
00166     return *this;
00167   }
00168   
00170   Self& operator/=( const Self& rhs )
00171   {
00172     for ( size_t i=0; i<NDIM; ++i ) 
00173       this->m_Data[i] /= rhs[i];
00174     return *this;
00175   }
00176 
00178   const Self operator-() 
00179   { 
00180     Self minus;
00181     for ( size_t i=0; i<NDIM; ++i ) 
00182       minus.m_Data = -this->m_Data;
00183 
00184     return minus;
00185   }
00186   
00188   T* begin()
00189   {
00190     return this->m_Data;
00191   }
00192 
00194   T* end()
00195   {
00196     return this->m_Data+NDIM;
00197   }
00198 
00200   const T* begin() const
00201   {
00202     return this->m_Data;
00203   }
00204 
00206   const T* end() const
00207   {
00208     return this->m_Data+NDIM;
00209   }
00210 
00212   T MaxValue() const
00213   {
00214     return *(std::max_element( this->begin(), this->end() ) );
00215   }
00216 
00218   T MinValue() const
00219   {
00220     return *(std::min_element( this->begin(), this->end() ) );
00221   }
00222 
00224   T Sum() const 
00225   {
00226     T sum = this->m_Data[0];
00227     for ( size_t i = 1; i < NDIM; ++i )
00228       sum += this->m_Data[i];
00229 
00230     return sum;
00231   }
00232 
00234   T Product() const 
00235   {
00236     T product = this->m_Data[0];
00237     for ( size_t i = 1; i < NDIM; ++i )
00238       product *= this->m_Data[i];
00239 
00240     return product;
00241   }
00242 
00244   T SumOfSquares() const 
00245   {
00246     T sq = 0;
00247     for ( size_t i = 0; i < NDIM; ++i )
00248       sq += this->m_Data[i] * this->m_Data[i];
00249 
00250     return sq;
00251   }
00252 
00254   T MaxAbsValue() const 
00255   {
00256     T maxAbs = fabs( this->m_Data[0] );
00257     for ( size_t i = 1; i < NDIM; ++i )
00258       maxAbs = std::max<T>( maxAbs, fabs( this->m_Data[i] ) );
00259     
00260     return maxAbs;
00261   }
00262 
00264   T RootSumOfSquares() const 
00265   {
00266     return sqrt( this->SumOfSquares() );
00267   }
00268 
00269 private:
00271   T m_Data[NDIM];
00272 };
00273 
00275 template<size_t NDIM,typename T>
00276 const FixedVector<NDIM,T>
00277 operator+( const FixedVector<NDIM,T>& lhs, const FixedVector<NDIM,T>& rhs )
00278 {
00279   return FixedVector<NDIM,T>( lhs ) += rhs;
00280 }
00281 
00283 template<size_t NDIM,typename T>
00284 const FixedVector<NDIM,T>
00285 operator-( const FixedVector<NDIM,T>& lhs, const FixedVector<NDIM,T>& rhs )
00286 {
00287   return FixedVector<NDIM,T>( lhs ) -= rhs;
00288 }
00289 
00291 template<size_t NDIM,typename T>
00292 T
00293 operator* ( const FixedVector<NDIM,T> &lhs, const FixedVector<NDIM,T>& rhs ) 
00294 {
00295   T product = lhs[0] * rhs[0];
00296   for ( size_t i = 1; i<NDIM; ++i )
00297     product += lhs[i] * rhs[i];
00298   return product;
00299 }
00300 
00302 template<size_t NDIM,typename T,typename T2>
00303 const FixedVector<NDIM,T>
00304 operator*( const T2 lhs, const FixedVector<NDIM,T>& rhs )
00305 {
00306   FixedVector<NDIM,T> result( rhs );
00307   for ( size_t i = 0; i<NDIM; ++i )
00308     result[i] *= lhs;
00309   return result;
00310 }
00311 
00313 template<size_t NDIM,typename T>
00314 std::ofstream& operator<<( std::ofstream& stream, const FixedVector<NDIM,T>& index )
00315 {
00316   for ( size_t i = 0; i < NDIM; ++i )
00317     stream << index[i];
00318   return stream;
00319 }
00320 
00322 template<size_t NDIM,typename T>
00323 std::ifstream& operator>>( std::ifstream& stream, FixedVector<NDIM,T>& index )
00324 {
00325   for ( size_t i = 0; i < NDIM; ++i )
00326     stream >> index[i];
00327   return stream;
00328 }
00329 
00331 template<size_t NDIM,typename T>
00332 class FixedVectorStaticInitializer
00333 {
00334 };
00335 
00337 template<typename T>
00338 class FixedVectorStaticInitializer<3,T>
00339 {
00340 public:
00342   typedef FixedVector<3,T> VectorType;
00343 
00345   static const VectorType Init( const T& x0, const T& x1, const T& x2 )
00346   {
00347     VectorType v;
00348 
00349     v[0] = x0;
00350     v[1] = x1;
00351     v[2] = x2;
00352     
00353     return v;
00354   }
00355 };
00356 
00357 } 
00358 
00359 #endif // #ifndef __cmtkFixedVector_h_included_