aimsalgo  5.1.2
Neuroimaging image processing
dynamic_d.h
Go to the documentation of this file.
1 /* This software and supporting documentation are distributed by
2  * Institut Federatif de Recherche 49
3  * CEA/NeuroSpin, Batiment 145,
4  * 91191 Gif-sur-Yvette cedex
5  * France
6  *
7  * This software is governed by the CeCILL-B license under
8  * French law and abiding by the rules of distribution of free software.
9  * You can use, modify and/or redistribute the software under the
10  * terms of the CeCILL-B license as circulated by CEA, CNRS
11  * and INRIA at the following URL "http://www.cecill.info".
12  *
13  * As a counterpart to the access to the source code and rights to copy,
14  * modify and redistribute granted by the license, users are provided only
15  * with a limited warranty and the software's author, the holder of the
16  * economic rights, and the successive licensors have only limited
17  * liability.
18  *
19  * In this respect, the user's attention is drawn to the risks associated
20  * with loading, using, modifying and/or developing or reproducing the
21  * software by the user in light of its specific status of free software,
22  * that may mean that it is complicated to manipulate, and that also
23  * therefore means that it is reserved for developers and experienced
24  * professionals having in-depth computer knowledge. Users are therefore
25  * encouraged to load and test the software's suitability as regards their
26  * requirements in conditions enabling the security of their systems and/or
27  * data to be ensured and, more generally, to use and operate it in the
28  * same conditions as regards security.
29  *
30  * The fact that you are presently reading this means that you have had
31  * knowledge of the CeCILL-B license and that you accept its terms.
32  */
33 #ifndef AIMSALGO_REGISTRATION_PREPROCESSING_D_H
34 #define AIMSALGO_REGISTRATION_PREPROCESSING_D_H
35 
36 #include <aims/utility/dynamic.h>
37 #include <aims/math/mathelem.h> // aims::MathUtil
38 #include <algorithm> // std::max_element
39 #include <limits>
40 #include <vector>
41 
42 namespace aims {
43 
44  //==========================================================================
45  // Utils
46  //==========================================================================
47  namespace util {
48 
49  template <typename T>
50  T epsilon()
51  {
53  return (T)1;
54  else
56  }
57  }
58 
59  //==========================================================================
60  // clip
61  //==========================================================================
62  template <typename T>
64  const T & min, const T & max,
65  bool in_place )
66  {
67  carto::VolumeRef<T> tmp = ( in_place ? in : in.deepcopy() );
68 
69  for( long t = 0; t < in.getSizeT(); ++t )
70  for( long z = 0; z < in.getSizeZ(); ++z )
71  for( long y = 0; y < in.getSizeY(); ++y )
72  for( long x = 0; x < in.getSizeX(); ++x )
73  {
74  T val = tmp(x, y, z, t);
75  if( val < min )
76  tmp(x, y, z, t) = min;
77  if( val > max )
78  tmp(x, y, z, t) = max;
79  }
80  return tmp;
81  }
82 
83  template <typename T>
85  const T & min, const T & max )
86  {
87  return clip( in.deepcopy(), min, max );
88  }
89 
90  //==========================================================================
91  // clipDynamic
92  //==========================================================================
93 
94  template <typename T>
96  bool flatten_mask,
97  float pct_kept )
98  {
99  carto::VolumeRef<T> out = in.deepcopy();
100  return clipDynamic( out, flatten_mask, pct_kept, true );
101  }
102 
103  template <typename T>
105  bool flatten_mask,
106  float pct_kept,
107  bool in_place )
108  {
109  carto::VolumeRef<T> vol = in;
110  if( !in_place )
111  vol = carto::deepcopy(in);
112 
113  T min, max;
114 
115  // Find second minimum
116  max = *std::max_element( vol.begin(), vol.end() );
117  if( flatten_mask )
118  {
119  min = max;
120  T trueMin = *std::min_element( vol.begin(), vol.end() );
121  for( int z = 0; z < vol.getSizeZ(); ++z )
122  for( int y = 0; y < vol.getSizeY(); ++y )
123  for( int x = 0; x < vol.getSizeX(); ++x )
124  {
125  if( vol(x, y, z) != trueMin && vol(x, y, z) < min )
126  min = vol(x, y, z);
127  }
128  }
129  else
130  min = *std::min_element( vol.begin(), vol.end() );
131 
132  // Find pct% max
133  if( pct_kept < 1. )
134  {
135  std::vector<long> histo( 100, 0 );
136  double histoDelta = double(max - min) / 99.;
137  for( int z = 0; z < vol.getSizeZ(); ++z )
138  for( int y = 0; y < vol.getSizeY(); ++y )
139  for( int x = 0; x < vol.getSizeX(); ++x )
140  {
141  T val = vol(x, y, z);
142  if( val >= min )
143  histo[ int( double(val - min) / histoDelta ) ] += 1;
144  }
145  long histoSize = aims::MathUtil<long>::sum( histo.begin(), histo.end() );
146  long accumulate = 0;
147  int i99 = 99;
148  while( i99 >= 0 && (double)accumulate / histoSize < 1. - pct_kept )
149  {
150  accumulate += histo[i99];
151  max = (T)(min + histoDelta * double(i99));
152  --i99;
153  }
154  histo.clear();
155  }
156 
157  if( flatten_mask )
158  min -= util::epsilon<T>();
159 
160  clip( vol, min, max );
161  return vol;
162  }
163 
164 } // namespace aims
165 
166 #endif // AIMSALGO_REGISTRATION_PREPROCESSING_D_H
static T sum(Iterator b, Iterator e)
int getSizeZ() const
VolumeRef< T > deepcopy() const
int getSizeT() const
iterator end()
int getSizeY() const
iterator begin()
int getSizeX() const
float min(float x, float y)
Definition: thickness.h:106
float max(float x, float y)
Definition: thickness.h:98
T epsilon()
Definition: dynamic_d.h:50
carto::VolumeRef< T > clip(const carto::VolumeRef< T > &in, const T &min, const T &max)
\function clip
Definition: dynamic_d.h:84
carto::VolumeRef< T > clipDynamic(const carto::VolumeRef< T > &in, bool flatten_mask=true, float pct_kept=1.)
\function clipDynamic
Definition: dynamic_d.h:95
OUTP accumulate(const Volume< T > &vol, BinaryFunction func, OUTP initial)
Volume< T > deepcopy(const Volume< T > &src, const std::vector< int > &size=std::vector< int >())
static _Tp epsilon()