ITK  4.1.0
Insight Segmentation and Registration Toolkit
itkVariableLengthVector.h
Go to the documentation of this file.
00001 /*=========================================================================
00002  *
00003  *  Copyright Insight Software Consortium
00004  *
00005  *  Licensed under the Apache License, Version 2.0 (the "License");
00006  *  you may not use this file except in compliance with the License.
00007  *  You may obtain a copy of the License at
00008  *
00009  *         http://www.apache.org/licenses/LICENSE-2.0.txt
00010  *
00011  *  Unless required by applicable law or agreed to in writing, software
00012  *  distributed under the License is distributed on an "AS IS" BASIS,
00013  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00014  *  See the License for the specific language governing permissions and
00015  *  limitations under the License.
00016  *
00017  *=========================================================================*/
00018 #ifndef __itkVariableLengthVector_h
00019 #define __itkVariableLengthVector_h
00020 
00021 #include "itkNumericTraits.h"
00022 
00023 namespace itk
00024 {
00075 template< typename TValueType >
00076 class VariableLengthVector
00077 {
00078 public:
00079 
00081   typedef TValueType                                    ValueType;
00082   typedef TValueType                                    ComponentType;
00083   typedef typename NumericTraits< ValueType >::RealType RealValueType;
00084   typedef VariableLengthVector                          Self;
00085 
00087   typedef unsigned int ElementIdentifier;
00088 
00091   VariableLengthVector();
00092 
00094   VariableLengthVector(unsigned int dimension);
00095 
00102   VariableLengthVector(ValueType *data, unsigned int sz,
00103                        bool LetArrayManageMemory = false);
00104 
00111   VariableLengthVector(const ValueType *data, unsigned int sz,
00112                        bool LetArrayManageMemory = false);
00113 
00123   template< class T >
00124   VariableLengthVector(const VariableLengthVector< T > & v)
00125   {
00126     m_NumElements = v.Size();
00127     m_Data = this->AllocateElements(m_NumElements);
00128     m_LetArrayManageMemory = true;
00129     for ( ElementIdentifier i = 0; i < v.Size(); i++ )
00130       {
00131       this->m_Data[i] = static_cast< ValueType >( v[i] );
00132       }
00133   }
00135 
00138   VariableLengthVector(const VariableLengthVector< TValueType > & v);
00139 
00141   void Fill(TValueType const & v);
00142 
00144   template< class T >
00145   const VariableLengthVector< TValueType > & operator=
00146     (const VariableLengthVector< T > & v)
00147   {
00148     if ( m_Data == static_cast< void * >( const_cast< T * >
00149                                           ( ( const_cast< VariableLengthVector< T > & >( v ) ).GetDataPointer() ) ) )
00150       {
00151       return *this;
00152       }
00153     this->SetSize( v.Size() );
00154     for ( ElementIdentifier i = 0; i < v.Size(); i++ )
00155       {
00156       this->m_Data[i] = static_cast< ValueType >( v[i] );
00157       }
00158     return *this;
00159   }
00161 
00163   const Self & operator=(const Self & v);
00164 
00165   const Self & operator=(TValueType const & v);
00166 
00168   inline unsigned int Size(void) const { return m_NumElements; }
00169   inline unsigned int GetNumberOfElements(void) const { return m_NumElements; }
00171 
00173   TValueType       & operator[](unsigned int i) { return this->m_Data[i]; }
00174 
00176   TValueType const & operator[](unsigned int i) const { return this->m_Data[i]; }
00177 
00179   inline const TValueType & GetElement(unsigned int i) const { return m_Data[i]; }
00180 
00182   void SetElement(unsigned int i, const TValueType & value) { m_Data[i] = value; }
00183 
00194   void SetSize(unsigned int sz, bool destroyExistingData = true);
00195 
00198   void DestroyExistingData();
00199 
00200   inline unsigned int GetSize(void) const { return m_NumElements; }
00201 
00207   void SetData(TValueType *data, bool LetArrayManageMemory = false);
00208 
00218   void SetData(TValueType *data, unsigned int sz, bool LetArrayManageMemory = false);
00219 
00222   ~VariableLengthVector();
00223 
00230   void Reserve(ElementIdentifier);
00231 
00233   TValueType * AllocateElements(ElementIdentifier size) const;
00234 
00235   const TValueType * GetDataPointer() const { return m_Data; }
00236 
00243   template< class T >
00244   inline Self operator+(const VariableLengthVector< T > & v) const
00245   {
00246     // if( m_NumElements != v.GetSize() )
00247     //   {
00248     //   itkGenericExceptionMacro( << "Cannot add VariableLengthVector of length
00249     // "
00250     //                             << m_NumElements " and " << v.GetSize() );
00251     //   }
00252     const ElementIdentifier length = v.Size();
00253     Self                    result(length);
00255 
00256     for ( ElementIdentifier i = 0; i < length; i++ )
00257       {
00258       result[i] = ( *this )[i] + static_cast< ValueType >( v[i] );
00259       }
00260     return result;
00261   }
00262 
00270   template< class T >
00271   inline Self operator-(const VariableLengthVector< T > & v) const
00272   {
00273     // if( m_NumElements != v.GetSize() )
00274     //   {
00275     //   itkGenericExceptionMacro( << "Cannot add VariableLengthVector of length
00276     // "
00277     //                             << m_NumElements " and " << v.GetSize() );
00278     //   }
00279     const ElementIdentifier length = v.Size();
00280     Self                    result(length);
00282 
00283     for ( ElementIdentifier i = 0; i < length; i++ )
00284       {
00285       result[i] = ( *this )[i] - static_cast< ValueType >( v[i] );
00286       }
00287     return result;
00288   }
00289 
00294   template< class T >
00295   inline Self operator*(T s) const
00296   {
00297     Self result(m_NumElements);
00298 
00299     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00300       {
00301       result[i] = m_Data[i] * static_cast< ValueType >( s );
00302       }
00303     return result;
00304   }
00305 
00310   template< class T >
00311   inline Self operator/(T s) const
00312   {
00313     Self result(m_NumElements);
00314 
00315     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00316       {
00317       result[i] = static_cast< ValueType >(
00318         static_cast< RealValueType >( m_Data[i] )
00319         / static_cast< RealValueType >( s ) );
00320       }
00321     return result;
00322   }
00323 
00325   inline Self operator+(TValueType s) const
00326   {
00327     Self result(m_NumElements);
00328 
00329     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00330       {
00331       result[i] = m_Data[i] + s;
00332       }
00333     return result;
00334   }
00335 
00337   inline Self operator-(TValueType s) const
00338   {
00339     Self result(m_NumElements);
00340 
00341     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00342       {
00343       result[i] = m_Data[i] - s;
00344       }
00345     return result;
00346   }
00347 
00350   inline Self & operator--()
00351   {
00352     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00353       {
00354       this->m_Data[i] -= static_cast< ValueType >( 1.0 );
00355       }
00356     return *this;
00357   }
00359 
00361   inline Self & operator++() // prefix operator ++v;
00362   {
00363     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00364       {
00365       this->m_Data[i] += static_cast< ValueType >( 1.0 );
00366       }
00367     return *this;
00368   }
00370 
00373   inline Self operator--(int) // postfix operator v--;
00374   {
00375     Self tmp(*this);
00377 
00378     --tmp;
00379     return tmp;
00380   }
00381 
00383   inline Self operator++(int) // postfix operator v++;
00384   {
00385     Self tmp(*this);
00387 
00388     ++tmp;
00389     return tmp;
00390   }
00391 
00399   template< class T >
00400   inline Self & operator-=
00401     (const VariableLengthVector< T > & v)
00402   {
00403     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00404       {
00405       m_Data[i] -= static_cast< ValueType >( v[i] );
00406       }
00407     return *this;
00408   }
00410 
00412   inline Self & operator-=(TValueType s)
00413   {
00414     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00415       {
00416       m_Data[i] -= s;
00417       }
00418     return *this;
00419   }
00421 
00429   template< class T >
00430   inline Self & operator+=
00431     (const VariableLengthVector< T > & v)
00432   {
00433     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00434       {
00435       m_Data[i] += static_cast< ValueType >( v[i] );
00436       }
00437     return *this;
00438   }
00440 
00442   inline Self & operator+=(TValueType s)
00443   {
00444     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00445       {
00446       m_Data[i] += s;
00447       }
00448     return *this;
00449   }
00451 
00455   template< class T >
00456   inline Self & operator*=(T s)
00457   {
00458     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00459       {
00460       m_Data[i] *= ( static_cast< ValueType >( s ) );
00461       }
00462     return *this;
00463   }
00465 
00470   template< class T >
00471   inline Self & operator/=(T s)
00472   {
00473     for ( ElementIdentifier i = 0; i < m_NumElements; i++ )
00474       {
00475       m_Data[i] = static_cast< ValueType >(
00476         static_cast< RealValueType >( m_Data[i] )
00477         / static_cast< RealValueType >( s ) );
00478       }
00479     return *this;
00480   }
00482 
00484   Self & operator-();  // negation operator
00485 
00486   bool operator==(const Self & v) const;
00487 
00488   bool operator!=(const Self & v) const;
00489 
00491   RealValueType GetNorm() const;
00492 
00494   RealValueType GetSquaredNorm() const;
00495 
00496 private:
00497 
00498   bool              m_LetArrayManageMemory; // if true, the array is responsible
00499                                             // for memory of data
00500   TValueType *      m_Data;                 // Array to hold data
00501   ElementIdentifier m_NumElements;
00502 };
00503 
00507 template< class TValueType, class T >
00508 inline
00509 VariableLengthVector< TValueType >
00510 operator*(const T & scalar, const VariableLengthVector< TValueType > & v)
00511 {
00512   return v * scalar;
00513 }
00514 
00515 template< typename TValueType >
00516 std::ostream & operator<<(std::ostream & os, const VariableLengthVector< TValueType > & arr)
00517 {
00518   const unsigned int length = arr.Size();
00519   const signed int   last   = (unsigned int)length - 1;
00520 
00521   os << "[";
00522   for ( signed int i = 0; i < last; ++i )
00523     {
00524     os << arr[i] << ", ";
00525     }
00526   if ( length >= 1 )
00527     {
00528     os << arr[last];
00529     }
00530   os << "]";
00531   return os;
00532 }
00533 } // namespace itk
00534 
00535 #include "itkNumericTraitsVariableLengthVectorPixel.h"
00536 
00537 // Define instantiation macro for this template.
00538 #define ITK_TEMPLATE_VariableLengthVector(_, EXPORT, TypeX, TypeY)                    \
00539   namespace itk                                                                       \
00540   {                                                                                   \
00541   _( 1 ( class EXPORT VariableLengthVector< ITK_TEMPLATE_1 TypeX > ) )                \
00542   namespace Templates                                                                 \
00543   {                                                                                   \
00544   typedef VariableLengthVector< ITK_TEMPLATE_1 TypeX > VariableLengthVector##TypeY; \
00545   }                                                                                   \
00546   }
00547 
00548 #if ITK_TEMPLATE_EXPLICIT
00549 #include "Templates/itkVariableLengthVector+-.h"
00550 #endif
00551 
00552 #if ITK_TEMPLATE_TXX
00553 #include "itkVariableLengthVector.hxx"
00554 #endif
00555 
00556 #endif
00557