Main Page   Groups   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Namespace Members   Compound Members   File Members   Concepts

itkMovingHistogramMorphologyImageFilter.h

Go to the documentation of this file.
00001 /*=========================================================================
00002 
00003   Program:   Insight Segmentation & Registration Toolkit
00004   Module:    $RCSfile: itkMovingHistogramMorphologyImageFilter.h,v $
00005   Language:  C++
00006   Date:      $Date: 2004/04/30 21:02:03 $
00007   Version:   $Revision: 1.15 $
00008 
00009   Copyright (c) Insight Software Consortium. All rights reserved.
00010   See ITKCopyright.txt or http://www.itk.org/HTML/Copyright.htm for details.
00011 
00012      This software is distributed WITHOUT ANY WARRANTY; without even 
00013      the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR 
00014      PURPOSE.  See the above copyright notices for more information.
00015 
00016 =========================================================================*/
00017 #ifndef __itkMovingHistogramMorphologyImageFilter_h
00018 #define __itkMovingHistogramMorphologyImageFilter_h
00019 
00020 #include "itkMovingHistogramImageFilter.h"
00021 #include <list>
00022 #include <map>
00023 #include "itkOffsetLexicographicCompare.h"
00024 
00025 namespace itk {
00026 
00027 namespace Function {
00028 template <class TInputPixel, class TCompare>
00029 class MorphologyHistogram
00030 {
00031 public:
00032   MorphologyHistogram()
00033     {
00034     if( useVectorBasedAlgorithm() )
00035       { initVector(); }
00036     }
00037   ~MorphologyHistogram(){}
00038 
00039 
00040 
00041   // define the method required by the functor and dispatch to the specialized methods
00042 
00043 
00044   inline void AddBoundary()
00045     {
00046     if( useVectorBasedAlgorithm() )
00047       { AddBoundaryVector(); }
00048     else
00049       { AddBoundaryMap(); }
00050     }
00051 
00052   inline void RemoveBoundary()
00053     {
00054     if( useVectorBasedAlgorithm() )
00055       { RemoveBoundaryVector(); }
00056     else
00057       { RemoveBoundaryMap(); }
00058     }
00059 
00060   inline void AddPixel( const TInputPixel &p )
00061     {
00062     if( useVectorBasedAlgorithm() )
00063       { AddPixelVector( p ); }
00064     else
00065       { AddPixelMap( p ); }
00066     }
00067 
00068   inline void RemovePixel( const TInputPixel &p )
00069     {
00070     if( useVectorBasedAlgorithm() )
00071       { RemovePixelVector( p ); }
00072     else
00073       { RemovePixelMap( p ); }
00074     }
00075 
00076   inline TInputPixel GetValue()
00077     {
00078     if( useVectorBasedAlgorithm() )
00079       { return GetValueVector(); }
00080     else
00081       { return GetValueMap(); }
00082     }
00083 
00084 
00085   inline bool useVectorBasedAlgorithm()
00086     {
00087     // bool, short and char are acceptable for vector based algorithm: they do not require
00088     // too much memory. Other types are not usable with that algorithm
00089     return typeid(TInputPixel) == typeid(unsigned char)
00090         || typeid(TInputPixel) == typeid(signed char)
00091         || typeid(TInputPixel) == typeid(unsigned short)
00092         || typeid(TInputPixel) == typeid(signed short)
00093         || typeid(TInputPixel) == typeid(bool);
00094     }
00095 
00096 
00097 
00098   //
00099   // the map based algorithm
00100   //
00101 
00102   typedef typename std::map< TInputPixel, unsigned long, TCompare > MapType;
00103 
00104   inline void AddBoundaryMap()
00105     { m_Map[ m_Boundary ]++; }
00106 
00107   inline void RemoveBoundaryMap()
00108     { m_Map[ m_Boundary ]--; }
00109 
00110   inline void AddPixelMap( const TInputPixel &p )
00111     { m_Map[ p ]++; }
00112 
00113   inline void RemovePixelMap( const TInputPixel &p )
00114     { m_Map[ p ]--; }
00115 
00116   inline TInputPixel GetValueMap()
00117     {
00118     // clean the map
00119     typename MapType::iterator mapIt = m_Map.begin();
00120     while( mapIt != m_Map.end() )
00121       {
00122       if( mapIt->second == 0 )
00123         { 
00124         // this value must be removed from the histogram
00125         // The value must be stored and the iterator updated before removing the value
00126         // or the iterator is invalidated.
00127         TInputPixel toErase = mapIt->first;
00128         mapIt++;
00129         m_Map.erase( toErase );
00130         }
00131       else
00132         {
00133         mapIt++;
00134         // don't remove all the zero value found, just remove the one before the current maximum value
00135         // the histogram may become quite big on real type image, but it's an important increase of performances
00136         break;
00137         }
00138       }
00139 
00140     // and return the value
00141     return m_Map.begin()->first;
00142     }
00143 
00144   MapType m_Map;
00145 
00146 
00147 
00148 
00149   //
00150   // the vector based algorithm
00151   //
00152 
00153   inline void initVector()
00154     {
00155     // initialize members need for the vector based algorithm
00156     m_Vector.resize( static_cast<int>( NumericTraits< TInputPixel >::max() - NumericTraits< TInputPixel >::NonpositiveMin() + 1 ), 0 );
00157     if( m_Compare( NumericTraits< TInputPixel >::max(), NumericTraits< TInputPixel >::NonpositiveMin() ) )
00158       {
00159       m_CurrentValue = NumericTraits< TInputPixel >::NonpositiveMin();
00160       m_Direction = -1;
00161       }
00162     else
00163       {
00164       m_CurrentValue = NumericTraits< TInputPixel >::max();
00165       m_Direction = 1;
00166       }
00167     }
00168   
00169 
00170   inline void AddBoundaryVector()
00171     { AddPixelVector( m_Boundary ); }
00172 
00173   inline void RemoveBoundaryVector()
00174     { RemovePixelVector( m_Boundary ); }
00175 
00176   inline void AddPixelVector( const TInputPixel &p )
00177     {
00178     m_Vector[ static_cast<int>( p - NumericTraits< TInputPixel >::NonpositiveMin() ) ]++;
00179     if( m_Compare( p, m_CurrentValue ) )
00180       { m_CurrentValue = p; }
00181     }
00182 
00183   inline void RemovePixelVector( const TInputPixel &p )
00184     {
00185     m_Vector[ static_cast<int>( p - NumericTraits< TInputPixel >::NonpositiveMin() ) ]--;
00186     while( m_Vector[ static_cast<int>( m_CurrentValue - NumericTraits< TInputPixel >::NonpositiveMin() ) ] == 0 )
00187       { m_CurrentValue += m_Direction; }
00188     }
00189 
00190   inline TInputPixel GetValueVector()
00191     { return m_CurrentValue; }
00192 
00193   std::vector<unsigned long> m_Vector;
00194   TInputPixel m_CurrentValue;
00195   TCompare m_Compare;
00196   signed int m_Direction;
00197 
00198 
00199 
00200   // accessor for boundary value
00201 
00202   void SetBoundary( const TInputPixel & val )
00203     { m_Boundary = val; }
00204 
00205   TInputPixel m_Boundary;
00206 };
00207 } // end namespace Function
00208 
00209 
00210 
00222 template<class TInputImage, class TOutputImage, class TKernel, class THistogram>
00223 class ITK_EXPORT MovingHistogramMorphologyImageFilter : 
00224     public MovingHistogramImageFilter<TInputImage, TOutputImage, TKernel, THistogram>
00225 {
00226 public:
00228   typedef MovingHistogramMorphologyImageFilter Self;
00229   typedef MovingHistogramImageFilter<TInputImage, TOutputImage, TKernel, THistogram> Superclass;
00230   typedef SmartPointer<Self>        Pointer;
00231   typedef SmartPointer<const Self>  ConstPointer;
00232 
00234   itkNewMacro(Self);  
00235 
00237   itkTypeMacro(MovingHistogramMorphologyImageFilter, 
00238                ImageToImageFilter);
00239 
00241   typedef TInputImage InputImageType;
00242   typedef TOutputImage OutputImageType;
00243   typedef typename TInputImage::RegionType RegionType ;
00244   typedef typename TInputImage::SizeType SizeType ;
00245   typedef typename TInputImage::IndexType IndexType ;
00246   typedef typename TInputImage::PixelType PixelType ;
00247   typedef typename TInputImage::OffsetType OffsetType ;
00248   typedef typename Superclass::OutputImageRegionType OutputImageRegionType;
00249   typedef typename TOutputImage::PixelType OutputPixelType ;
00250 
00252   itkStaticConstMacro(ImageDimension, unsigned int,
00253                       TInputImage::ImageDimension);
00254 
00256   typedef TKernel KernelType;
00257 
00259   typedef typename KernelType::ConstIterator KernelIteratorType ;
00260 
00262   typedef typename KernelType::SizeType RadiusType ;
00263 
00264   typedef typename std::list< OffsetType > OffsetListType;
00265 
00266   typedef typename std::map< OffsetType, OffsetListType, typename Functor::OffsetLexicographicCompare<ImageDimension> > OffsetMapType;
00267 
00269   itkSetMacro(Boundary, PixelType);
00270   itkGetMacro(Boundary, PixelType);
00272 
00273 protected:
00274   MovingHistogramMorphologyImageFilter();
00275   ~MovingHistogramMorphologyImageFilter() {};
00276   void PrintSelf(std::ostream& os, Indent indent) const;
00277   
00279 //   void  ThreadedGenerateData (const OutputImageRegionType& 
00280 //                               outputRegionForThread,
00281 //                               int threadId) ;
00282 
00284   virtual THistogram NewHistogram();
00285 
00286   PixelType m_Boundary;
00287 
00288 private:
00289   MovingHistogramMorphologyImageFilter(const Self&); //purposely not implemented
00290   void operator=(const Self&); //purposely not implemented
00291 
00292 } ; // end of class
00293 
00294 } // end namespace itk
00295   
00296 #ifndef ITK_MANUAL_INSTANTIATION
00297 #include "itkMovingHistogramMorphologyImageFilter.txx"
00298 #endif
00299 
00300 #endif
00301 
00302 
00303 

Generated at Fri Sep 8 03:44:09 2006 for ITK by doxygen 1.4.7 written by Dimitri van Heesch, © 1997-2000