00001 /*========================================================================= 00002 00003 Program: Insight Segmentation & Registration Toolkit 00004 Module: $RCSfile: itkImageRandomNonRepeatingConstIteratorWithIndex.h,v $ 00005 Language: C++ 00006 Date: $Date: 2008-10-18 21:13:25 $ 00007 Version: $Revision: 1.8 $ 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 __itkImageRandomNonRepeatingConstIteratorWithIndex_h 00018 #define __itkImageRandomNonRepeatingConstIteratorWithIndex_h 00019 00020 #include "itkImageConstIteratorWithIndex.h" 00021 #include "itkImage.h" 00022 #include <algorithm> 00023 #include <iostream> 00024 #include "itkMersenneTwisterRandomVariateGenerator.h" 00025 00026 00027 namespace itk 00028 { 00029 00030 00040 class NodeOfPermutation 00041 { 00042 public: 00043 unsigned long m_Priority; 00044 unsigned long m_Index; 00045 double m_Value; 00046 00047 NodeOfPermutation () 00048 { 00049 m_Priority=0; 00050 m_Index=0; 00051 m_Value=0.0; 00052 } 00053 00054 bool operator<( const NodeOfPermutation& b) const 00055 { 00056 if(m_Priority==b.m_Priority) 00057 { 00058 return m_Value < b.m_Value; 00059 } 00060 else 00061 { 00062 return m_Priority < b.m_Priority; 00063 } 00064 } 00065 }; 00066 00067 00069 class RandomPermutation 00070 { 00071 public: 00072 typedef Statistics::MersenneTwisterRandomVariateGenerator::Pointer GeneratorPointer; 00073 NodeOfPermutation * m_Permutation; 00074 GeneratorPointer m_Generator; 00075 unsigned long m_Size; 00076 00077 RandomPermutation(unsigned long sz) 00078 { 00079 m_Size = sz; 00080 m_Permutation = new NodeOfPermutation[m_Size]; 00081 m_Generator = Statistics::MersenneTwisterRandomVariateGenerator::New(); 00082 this->Shuffle(); 00083 } 00084 00085 void Dump() 00086 { 00087 for(unsigned int i=0;i<m_Size;i++) 00088 { 00089 std::cout<<m_Permutation[i].m_Value<<" "<<m_Permutation[i].m_Priority 00090 <<" "<<m_Permutation[i].m_Index<<";"; 00091 std::cout<<std::endl; 00092 } 00093 } 00094 00095 void SetPriority(unsigned long i,unsigned long priority) 00096 { 00097 if(i>m_Size) 00098 { 00099 std::cerr<<"Error - i dont have "<<i<<" elements"<<std::endl; 00100 } 00101 else 00102 { 00103 m_Permutation[i].m_Priority = priority; 00104 } 00105 } 00106 00107 void Shuffle() 00108 { 00109 for(unsigned int i=0; i < m_Size; i++ ) 00110 { 00111 m_Permutation[i].m_Value = m_Generator->GetVariateWithClosedRange ( 1.0 ); 00112 m_Permutation[i].m_Index=i; 00113 } 00114 std::sort(m_Permutation,m_Permutation+m_Size); 00115 } 00116 00117 unsigned long operator[](unsigned long i) 00118 { 00119 return m_Permutation[i].m_Index; 00120 } 00121 00122 ~RandomPermutation() 00123 { 00124 delete [] m_Permutation; 00125 } 00126 00128 void ReinitializeSeed() 00129 { 00130 m_Generator->Initialize(); 00131 } 00132 00133 void ReinitializeSeed(int seed) 00134 { 00135 m_Generator->Initialize ( seed ); 00136 } 00137 }; 00138 00139 00207 template<typename TImage> 00208 class ITK_EXPORT ImageRandomNonRepeatingConstIteratorWithIndex : public ImageConstIteratorWithIndex<TImage> 00209 { 00210 public: 00212 typedef ImageRandomNonRepeatingConstIteratorWithIndex Self; 00213 typedef ImageConstIteratorWithIndex<TImage> Superclass; 00214 00219 typedef typename TImage::IndexType IndexType; 00220 00225 typedef typename TImage::RegionType RegionType; 00226 00231 typedef TImage ImageType; 00232 00236 typedef typename TImage::PixelContainer PixelContainer; 00237 typedef typename PixelContainer::Pointer PixelContainerPointer; 00238 00240 ImageRandomNonRepeatingConstIteratorWithIndex(); 00241 ~ImageRandomNonRepeatingConstIteratorWithIndex() 00242 { 00243 if( m_Permutation ) 00244 { 00245 delete m_Permutation; 00246 } 00247 } 00249 00252 ImageRandomNonRepeatingConstIteratorWithIndex(const ImageType *ptr, const RegionType& region); 00253 00260 ImageRandomNonRepeatingConstIteratorWithIndex( const ImageConstIteratorWithIndex<TImage> &it) 00261 { 00262 this->ImageConstIteratorWithIndex<TImage>::operator=(it); 00263 m_Permutation = NULL; 00264 } 00265 00267 void GoToBegin(void) 00268 { 00269 m_NumberOfSamplesDone = 0L; 00270 this->UpdatePosition(); 00271 } 00273 00275 void GoToEnd(void) 00276 { 00277 m_NumberOfSamplesDone = m_NumberOfSamplesRequested; 00278 this->UpdatePosition(); 00279 } 00281 00283 bool IsAtBegin(void) const 00284 { 00285 return (m_NumberOfSamplesDone == 0L); 00286 } 00287 00289 bool IsAtEnd(void) const 00290 { 00291 return (m_NumberOfSamplesDone >= m_NumberOfSamplesRequested); 00292 } 00293 00294 00296 itkStaticConstMacro( ImageDimension, unsigned int, ::itk::GetImageDimension< TImage >::ImageDimension ); 00297 00298 00300 typedef itk::Image< unsigned long, itkGetStaticConstMacro(ImageDimension ) > PriorityImageType; 00301 00307 void SetPriorityImage(const PriorityImageType * priorityImage); 00308 00311 Self & operator++() 00312 { 00313 m_NumberOfSamplesDone++; 00314 this->UpdatePosition(); 00315 return *this; 00316 } 00318 00321 Self & operator--() 00322 { 00323 m_NumberOfSamplesDone--; 00324 this->UpdatePosition(); 00325 return *this; 00326 } 00328 00330 void SetNumberOfSamples( unsigned long number ); 00331 unsigned long GetNumberOfSamples( void ) const; 00333 00335 void ReinitializeSeed(); 00336 00339 void ReinitializeSeed(int); 00340 00341 private: 00342 void UpdatePosition(); 00343 00344 unsigned long m_NumberOfSamplesRequested; 00345 unsigned long m_NumberOfSamplesDone; 00346 unsigned long m_NumberOfPixelsInRegion; 00347 RandomPermutation * m_Permutation; 00348 }; 00349 00350 } // end namespace itk 00351 00352 #ifndef ITK_MANUAL_INSTANTIATION 00353 #include "itkImageRandomNonRepeatingConstIteratorWithIndex.txx" 00354 #endif 00355 00356 #endif 00357