00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 #ifndef __itkMovingHistogramMorphologicalGradientImageFilter_h
00018 #define __itkMovingHistogramMorphologicalGradientImageFilter_h
00019
00020 #include "itkMovingHistogramImageFilter.h"
00021 #include <map>
00022
00023 namespace itk {
00024
00025 namespace Function {
00026 template <class TInputPixel>
00027 class MorphologicalGradientHistogram
00028 {
00029 public:
00030 MorphologicalGradientHistogram()
00031 {
00032 if( useVectorBasedAlgorithm() )
00033 { initVector(); }
00034 }
00035 ~MorphologicalGradientHistogram(){}
00036
00037 inline void AddBoundary() {}
00038
00039 inline void RemoveBoundary() {}
00040
00041 inline void AddPixel( const TInputPixel &p )
00042 {
00043 if( useVectorBasedAlgorithm() )
00044 { AddPixelVector( p ); }
00045 else
00046 { AddPixelMap( p ); }
00047 }
00048
00049 inline void RemovePixel( const TInputPixel &p )
00050 {
00051 if( useVectorBasedAlgorithm() )
00052 { RemovePixelVector( p ); }
00053 else
00054 { RemovePixelMap( p ); }
00055 }
00056
00057 inline TInputPixel GetValue()
00058 {
00059 if( useVectorBasedAlgorithm() )
00060 { return GetValueVector(); }
00061 else
00062 { return GetValueMap(); }
00063 }
00064
00065
00066 inline bool useVectorBasedAlgorithm()
00067 {
00068
00069
00070 return typeid(TInputPixel) == typeid(unsigned char)
00071 || typeid(TInputPixel) == typeid(signed char)
00072 || typeid(TInputPixel) == typeid(unsigned short)
00073 || typeid(TInputPixel) == typeid(signed short)
00074 || typeid(TInputPixel) == typeid(bool);
00075 }
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087 typedef typename std::map< TInputPixel, unsigned long > MapType;
00088
00089 inline void AddPixelMap( const TInputPixel &p )
00090 { m_Map[ p ]++; }
00091
00092 inline void RemovePixelMap( const TInputPixel &p )
00093 { m_Map[ p ]--; }
00094
00095 inline TInputPixel GetValueMap()
00096 {
00097
00098 typename MapType::iterator mapIt = m_Map.begin();
00099 while( mapIt != m_Map.end() )
00100 {
00101 if( mapIt->second == 0 )
00102 {
00103
00104
00105
00106 TInputPixel toErase = mapIt->first;
00107 mapIt++;
00108 m_Map.erase(toErase);
00109 }
00110 else
00111 {
00112 mapIt++;
00113 }
00114 }
00115
00116
00117 if( !m_Map.empty() )
00118 { return m_Map.rbegin()->first - m_Map.begin()->first; }
00119 return 0;
00120 }
00121
00122 MapType m_Map;
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134 inline void initVector()
00135 {
00136
00137 m_Vector.resize( static_cast<int>( NumericTraits< TInputPixel >::max() - NumericTraits< TInputPixel >::NonpositiveMin() + 1 ), 0 );
00138 m_Max = NumericTraits< TInputPixel >::NonpositiveMin();
00139 m_Min = NumericTraits< TInputPixel >::max();
00140 m_Count = 0;
00141 }
00142
00143 inline void AddPixelVector( const TInputPixel &p )
00144 {
00145 m_Vector[ static_cast<int>( p - NumericTraits< TInputPixel >::NonpositiveMin() ) ]++;
00146 if( p > m_Max )
00147 { m_Max = p; }
00148 if( p < m_Min )
00149 { m_Min = p; }
00150 m_Count++;
00151 }
00152
00153 inline void RemovePixelVector( const TInputPixel &p )
00154 {
00155 m_Vector[ static_cast<int>( p - NumericTraits< TInputPixel >::NonpositiveMin() ) ]--;
00156 m_Count--;
00157 if( m_Count > 0 )
00158 {
00159 while( m_Vector[ static_cast<int>( m_Max - NumericTraits< TInputPixel >::NonpositiveMin() ) ] == 0 )
00160 { m_Max--; }
00161 while( m_Vector[ static_cast<int>( m_Min - NumericTraits< TInputPixel >::NonpositiveMin() ) ] == 0 )
00162 { m_Min++; }
00163 }
00164 else
00165 {
00166 m_Max = NumericTraits< TInputPixel >::NonpositiveMin();
00167 m_Min = NumericTraits< TInputPixel >::max();
00168 }
00169 }
00170
00171 inline TInputPixel GetValueVector()
00172 {
00173 if( m_Count > 0 )
00174 { return m_Max - m_Min; }
00175 else
00176 { return NumericTraits< TInputPixel >::Zero; }
00177 }
00178
00179 std::vector<unsigned long> m_Vector;
00180 TInputPixel m_Min;
00181 TInputPixel m_Max;
00182 unsigned long m_Count;
00183
00184
00185
00186
00187 };
00188 }
00189
00204 template<class TInputImage, class TOutputImage, class TKernel>
00205 class ITK_EXPORT MovingHistogramMorphologicalGradientImageFilter :
00206 public MovingHistogramImageFilter<TInputImage, TOutputImage, TKernel,
00207 typename Function::MorphologicalGradientHistogram< typename TInputImage::PixelType > >
00208 {
00209 public:
00211 typedef MovingHistogramMorphologicalGradientImageFilter Self;
00212 typedef MovingHistogramImageFilter<TInputImage, TOutputImage, TKernel,
00213 typename Function::MorphologicalGradientHistogram< typename TInputImage::PixelType > > Superclass;
00214 typedef SmartPointer<Self> Pointer;
00215 typedef SmartPointer<const Self> ConstPointer;
00216
00218 itkNewMacro(Self);
00219
00221 itkTypeMacro(MovingHistogramMorphologicalGradientImageFilter,
00222 ImageToImageFilter);
00223
00225 typedef TInputImage InputImageType;
00226 typedef TOutputImage OutputImageType;
00227 typedef typename TInputImage::RegionType RegionType ;
00228 typedef typename TInputImage::SizeType SizeType ;
00229 typedef typename TInputImage::IndexType IndexType ;
00230 typedef typename TInputImage::PixelType PixelType ;
00231 typedef typename TInputImage::OffsetType OffsetType ;
00232 typedef typename Superclass::OutputImageRegionType OutputImageRegionType;
00233 typedef typename TOutputImage::PixelType OutputPixelType ;
00234
00235 typedef typename Function::MorphologicalGradientHistogram< PixelType > HistogramType;
00236
00237
00239 itkStaticConstMacro(ImageDimension, unsigned int,
00240 TInputImage::ImageDimension);
00241
00242
00243 protected:
00244 MovingHistogramMorphologicalGradientImageFilter() {};
00245 ~MovingHistogramMorphologicalGradientImageFilter() {};
00246
00247
00248 private:
00249 MovingHistogramMorphologicalGradientImageFilter(const Self&);
00250 void operator=(const Self&);
00251
00252 } ;
00253
00254 }
00255
00256 #endif
00257
00258
00259