| Bsoft 1.9 Bernard's software package

- Main Page
- Namespaces
- Classes
- Files

- File List
- File Members

All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
img_region_stats.cpp
Go to the documentation of this file.
1
9 #include "rwimg.h"
10 #include "matrix_linear.h"
11 #include "Complex.h"
12 #include "Vector3.h"
13 #include "utilities.h"
14
15 // Declaration of global variables
16 extern int verbose; // Level of output to the screen
17
29 int img_stats_within_radii(Bimage *p, double rad_min, double rad_max)
30 {
31 if ( !p ) {
32 cerr << "Error: No image in memory!" << endl;
33 return -1;
34 }
35
36 if ( !p->data_pointer() ) {
37 cerr << "Error: No data for image " << p->file_name() << " in memory!" << endl;
38 return -1;
39 }
40
41 unsigned long i, x, y, z, c, n;
42 unsigned long datasize = p->data_size();
43 double dx, dy, dz, d2, rmax2 = rad_max*rad_max, rmin2 = rad_min*rad_min;
44 double value, sum(0), ssum(0), w(0), min, max, avg, std;
45
46 if ( verbose & VERB_DEBUG ) {
47 cout << "DEBUG img_stats_within_radii: Data size: " << p->size() << "x" << p->channels() << "x" << p->images() << "=" << datasize << endl;
48 cout << "DEBUG img_stats_within_radii: datatype=" << p->data_type() << endl;
49 cout << "DEBUG img_stats_within_radii: min=" << p->minimum() << " max=" << p->maximum() << endl;
50 cout << "DEBUG img_stats_within_radii: ave=" << p->average() << " std=" << p->standard_deviation() << endl;
51 cout << "DEBUG img_stats_within_radii: fommax=" << p->FOM_maximum() << endl;
52 }
53
54 p->FOM_find_maximum();
55
56 min = 1e37;
57 max = -1e37;
58 for ( n=0; n<p->images(); n++ ) {
59 for ( z=0; z<p->sizeZ(); z++ ) {
60 dz = z - p->image[n].origin().z();
61 dz *= dz;
62 if ( dz <= rmax2 ) for ( y=0; y<p->sizeY(); y++ ) {
63 dy = y - p->image[n].origin().y();
64 dy *= dy;
65 if ( dy <= rmax2 ) for ( x=0; x<p->sizeX(); x++ ) {
66 dx = x - p->image[n].origin().x();
67 dx *= dx;
68 d2 = dx + dy + dz;
69 if ( d2 <= rmax2 && d2 >= rmin2 ) {
70 value = 0;
71 // i = ((n*p->sizeZ() + z)*p->sizeY() + y)*p->x + x;
72 i = p->index(0,x,y,z,n);
73 for ( c=0; c<p->channels(); c++, i++ ) {
74 value = (*p)[i];
75 sum += value;
76 ssum += value*value;
77 w += 1;
78 if ( min > value ) min = value;
79 if ( max < value ) max = value;
80 }
81 }
82 }
83 }
84 }
85 }
86
87 if ( w ) {
88 avg = sum/w;
89 std = ssum/w - avg*avg;
90 if ( std > 0 ) std = sqrt(std);
91 else std = 0;
92 }
93
94 p->show_minimum(min);
95 p->show_maximum(max);
96
97 if ( verbose & VERB_STATS ) {
98 cout << "Data size: " << p->size() << "x" << p->channels() << "x" << p->images() << "=" << w << endl;
99 cout << "Min, max, avg, std: " <<
100 p->minimum() << " " << p->maximum() << " " << p->average() << " " << p->standard_deviation() << endl << endl;
101 }
102
103 return 0;
104 }
105
121 int img_stats_in_box(Bimage* p, int img_num, Vector3<int> start, Vector3<int> end,
122 int type, double& avg, double& std)
123 {
124 int inc, n;
125 unsigned long i, x, y, z;
126 double a(1), b(1), c(1), fx, fy, fz;
127 double value, sum(0), sum2(0);
128
129 if ( verbose & VERB_DEBUG ) {
130 cout << "DEBUG img_stats_in_box: start=" << start << endl;
131 cout << "DEBUG img_stats_in_box: end=" << end << endl;
132 }
133
134 avg = std = 0;
135 if ( ( start.x() < 0 ) && ( end.x() < 0 ) ) return 0;
136 if ( ( start.y() < 0 ) && ( end.y() < 0 ) ) return 0;
137 if ( ( start.z() < 0 ) && ( end.z() < 0 ) ) return 0;
138 if ( ( start.x() >= p->sizeX() ) && ( end.x() >= p->sizeX() ) ) return 0;
139 if ( ( start.y() >= p->sizeY() ) && ( end.y() >= p->sizeY() ) ) return 0;
140 // if ( ( start.z() >= p->sizeZ() ) && ( end.z() >= p->sizeZ() ) ) return 0;
141 start = start.max(0);
142 end = end.max(0);
143 if ( start.x() >= p->sizeX() ) start[0] = p->sizeX() - 1;
144 if ( start.y() >= p->sizeY() ) start[1] = p->sizeY() - 1;
145 if ( start.z() >= p->sizeZ() ) start[2] = p->sizeZ() - 1;
146 if ( end.x() >= p->sizeX() ) end[0] = p->sizeX() - 1;
147 if ( end.y() >= p->sizeY() ) end[1] = p->sizeY() - 1;
148 if ( end.z() >= p->sizeZ() ) end[2] = p->sizeZ() - 1;
149 if ( start.x() > end.x() ) swap(start[0], end[0]);
150 if ( start.y() > end.y() ) swap(start[1], end[1]);
151 if ( start.z() > end.z() ) swap(start[2], end[2]);
152
153 Vector3<int> size = end - start;
154 Vector3<float> center;
155 if ( type == 2 ) {
156 if ( size.x() ) end[0] += 1;
157 if ( size.y() ) end[1] += 1;
158 if ( size.z() ) end[2] += 1;
159 }
160 size = end - start;
161 center = start + size/2.0;
162 if ( size.x() ) a = 2.0/size.x();
163 if ( size.y() ) b = 2.0/size.y();
164 if ( size.z() ) c = 2.0/size.z();
165
166 if ( verbose & VERB_DEBUG ) {
167 cout << "DEBUG img_stats_in_box: start=" << start << endl;
168 cout << "DEBUG img_stats_in_box: end=" << end << endl;
169 cout << "DEBUG img_stats_in_box: center=" << center << endl;
170 }
171
172 for ( n=0, z=start.z(); z<=end.z(); z++ ) {
173 fz = (z - center.z()) * c;
174 fz *= fz;
175 for ( y=start.y(); y<=end.y(); y++ ) {
176 fy = (y - center.y()) * b;
177 fy *= fy;
178 for ( x=start.x(); x<=end.x(); x++ ) {
179 fx = (x - center.x()) * a;
180 fx *= fx;
181 inc = 1;
182 if ( type == 2 && fx + fy + fz > 1 ) inc = 0;
183 if ( inc ) {
184 i = p->index(0,x,y,z,img_num);
185 value = (*p)[i];
186 sum += value;
187 sum2 += value*value;
188 n++;
189 }
190 }
191 }
192 }
193
194 if ( n ) {
195 avg = sum/n;
196 std = (sum2 - sum*sum/n)/n;
197 if ( std > 0 ) std = sqrt(std);
198 else std = 0;
199 }
200
201 if ( verbose & VERB_DEBUG )
202 cout << "DEBUG img_stats_in_box: n=" << n << " avg=" << avg << " std=" << std << endl;
203
204 return n;
205 }
206
207 /*
208 @brief Determines if a vector is inside or outside a polyhedral structure.
209
210 Whether a point is inside or outside is based on the polygon edges.
211 First the normal to an edge is calculated and tested whether it points
212 inside or outside the polygon by finding the distance to the center:
213 dist_cent = normal . edge_vertex
214 which must be positive. Then the distance to the given point is:
215 dist = normal . (edge_vertex - point)
216 The minimum distance gives the distance of the point to the closest edge.
217 If this distance is positive, the point is inside the polygon.
218 Requirement: The polygon vertices must be given in order of connectivity.
219 @param vec vector to test for.
220 int nvert number of vertices.
221 int ndim number of dimensions.
222 Vector3<float>* poly set of vertices.
223 @return double distance from closest edge (inside positive).
224 **/
225 double vector3_inside_outside(Vector3<float> vec, int ndim, int nvert, Vector3<float>* poly)
226 {
227 int i, j;
228 double d, dmin;
229 Vector3<float> normal;
230
231 // Find the closest edge
232 dmin = 1e30;
233 for ( i=0, j=1; i<nvert; i++, j++ ) {
234 if ( j >= nvert ) j = 0;
235 normal = poly[i] - poly[j];
236 normal = Vector3<float>(-normal.y(), normal.x(), 0);
237 normal.normalize();
238 if ( normal.scalar(poly[i]) < 0 ) normal = -normal;
239 d = normal.scalar(poly[i] - vec);
240 if ( dmin > d ) dmin = d;
241 }
242
243 return dmin;
244 }
245
260 int img_stats_in_poly(Bimage* p, int img_num, int nvert, Vector3<float>* poly,
261 double& avg, double& std)
262 {
263 int ndim, inc, n;
264 unsigned long i, x, y, z, c;
265 unsigned long image_size = p->sizeX()*p->sizeY()*p->sizeZ()*p->channels();
266 double value, d, dmin(1e30), dmax(0), sum(0), sum2(0);
267 Vector3<float> center, var, vec;
268
269 for ( i=0; i<nvert; i++ ) center += poly[i];
270
271 center /= nvert;
272
273 for ( i=0; i<nvert; i++ ) {
274 poly[i] -= center;
275 var += poly[i]*poly[i];
276 d = poly[i].length();
277 if ( dmin > d ) dmin = d;
278 if ( dmax < d ) dmax = d;
279 }
280
281 for ( i=0, ndim=0; i<3; i++ ) if ( var[i] > 0 ) ndim++;
282
283 if ( verbose & VERB_DEBUG ) {
284 cout << "DEBUG img_stats_in_poly: center=" << center << endl;
285 cout << "DEBUG img_stats_in_poly: ndim=" << ndim << " dmin=" << dmin << " dmax=" << dmax << endl;
286 }
287
288 for ( i = img_num*image_size, n=z=0; z<p->sizeZ(); z++ ) {
289 vec[2] = z - center.z();
290 for ( y=0; y<p->sizeY(); y++ ) {
291 vec[1] = y - center.y();
292 for ( x=0; x<p->sizeX(); x++ ) {
293 vec[0] = x - center.x();
294 d = vec.length();
295 inc = 0;
296 if ( d <= dmax ) {
297 if ( dmax == 0 ) inc = 1;
298 else if ( vector3_inside_outside(vec, ndim, nvert, poly) > 0 )
299 inc = 1;
300 }
301 for ( c=0; c<p->channels(); c++, i++ ) if ( inc ) {
302 value = (*p)[i];
303 sum += value;
304 sum2 += value*value;
305 n++;
306 }
307 }
308 }
309 }
310
311 avg = std = 0;
312 if ( n ) {
313 avg = sum/n;
314 std = (sum2 - sum*sum/n)/n;
315 if ( std > 0 ) std = sqrt(std);
316 else std = 0;
317 }
318
319 if ( verbose & VERB_DEBUG )
320 cout << "DEBUG img_stats_in_poly: n=" << n << " avg=" << avg << " std=" << std << endl;
321
322 return n;
323 }
324
331 int img_calculate_masked_statistics(Bimage* p, Bimage* pmask)
332 {
333 if ( !pmask ) return 0;
334
335 int lev;
336 int nlevel = (int) (pmask->maximum() + 1.5);
337 unsigned long i, imagesize = p->image_size();
338 double avg, std;
339 long* cnt = new long[nlevel];
340 double* sum = new double[nlevel];
341 double* sum2 = new double[nlevel];
342
343 for ( lev=0; lev<nlevel; lev++ ) sum[lev] = sum2[lev] = cnt[lev] = 0;
344
345 for ( i=0; i<imagesize; i++ ) {
346 lev = (int) ((*pmask)[i] + 0.5);
347 cnt[lev]++;
348 sum[lev] += (*p)[i];
349 sum2[lev] += (*p)[i] * (*p)[i];
350 }
351
352 cout << "Level\tCount\tSum\tAverage\tStDev" << endl;
353 for ( lev=0; lev<nlevel; lev++ ) {
354 avg = std = 0;
355 if ( cnt[lev] ) {
356 avg = sum[lev]/cnt[lev];
357 std = sum2[lev]/cnt[lev] - avg*avg;
358 if ( std > 0 ) std = sqrt(std);
359 else std = 0;
360 }
361 cout << lev << tab << cnt[lev] << tab << sum[lev] << tab << avg << tab << std << endl;
362 }
363
364 return nlevel;
365 }
366
Vector3::z
Type z()
Definition: Vector3.h:141
VERB_STATS
#define VERB_STATS
Definition: utilities.h:100
Bimage::sizeZ
void sizeZ(size_t nz)
Definition: Bimage.h:383
img_calculate_masked_statistics
int img_calculate_masked_statistics(Bimage *p, Bimage *pmask)
Calculates the statistics for an image for each level in a mask.
Definition: img_region_stats.cpp:331
Vector3::length
double length()
Definition: Vector3.h:198
utilities.h
Header file for general utilities.
VERB_DEBUG
#define VERB_DEBUG
Definition: utilities.h:104
Complex.h
Class for complex numbers.
Vector3< int >
std
Bimage::index
size_t index(size_t nx, size_t ny)
Definition: Bimage.h:387
Vector3::max
Type max()
Definition: Vector3.h:151
Bimage::average
double average(size_t cc, double xf, double yf, double zf, size_t nn, double iscale)
Averages in the xy plane when scaling is less than 1.
Definition: Bimage.cpp:1150
Bimage::FOM_find_maximum
double FOM_find_maximum()
Calculates the maximum in the FOM block.
Definition: Bimage.cpp:612
b
long b
Definition: jpegint.h:371
verbose
int verbose
Bimage::size
Vector3< int > size()
Definition: Bimage.h:378
Bimage
General image parameter class.
Definition: Bimage.h:150
img_stats_within_radii
int img_stats_within_radii(Bimage *p, double rad_min, double rad_max)
Calculates the statistics for an image with given radii.
Definition: img_region_stats.cpp:29
Bimage::maximum
double maximum()
Definition: Bimage.h:478
Bimage::channels
size_t channels()
Definition: Bimage.h:376
Bimage::image_size
size_t image_size()
Definition: Bimage.h:234
Vector3::scalar
double scalar(const Vector3 &v) const
Definition: Vector3.h:219
Bimage::show_maximum
double show_maximum()
Definition: Bimage.h:494
Vector3::x
Type x()
Definition: Vector3.h:139
Bimage::file_name
void file_name(Bstring s)
Definition: Bimage.h:212
Bsub_image::origin
void origin(double x, double y, double z)
Definition: Bimage.h:130
vector3_inside_outside
double vector3_inside_outside(Vector3< float > vec, int ndim, int nvert, Vector3< float > *poly)
Definition: img_region_stats.cpp:225
Bimage::FOM_maximum
double FOM_maximum()
Definition: Bimage.h:238
Bimage::standard_deviation
double standard_deviation()
Definition: Bimage.h:480
Bimage::images
size_t images()
Definition: Bimage.h:460
img_stats_in_poly
int img_stats_in_poly(Bimage *p, int img_num, int nvert, Vector3< float > *poly, double &avg, double &std)
Calculates the statistics for an image within the given polyhedron.
Definition: img_region_stats.cpp:260
Bimage::data_pointer
unsigned char * data_pointer()
Definition: Bimage.h:228
Bimage::data_size
size_t data_size()
Definition: Bimage.h:222
Bimage::sizeX
void sizeX(size_t nx)
Definition: Bimage.h:381
matrix_linear.h
Header file for matrix functions.
Vector3::normalize
double normalize()
Definition: Vector3.h:208
img_stats_in_box
int img_stats_in_box(Bimage *p, int img_num, Vector3< int > start, Vector3< int > end, int type, double &avg, double &std)
Calculates the statistics for an image within the given box.
Definition: img_region_stats.cpp:121
Bimage::sizeY
void sizeY(size_t ny)
Definition: Bimage.h:382
Vector3.h
Class for 3-value vectors.
rwimg.h
Header file for 2D and 3D image I/O.
Bimage::show_minimum
double show_minimum()
Definition: Bimage.h:493
Bimage::data_type
DataType data_type()
Definition: Bimage.h:292
Vector3::y
Type y()
Definition: Vector3.h:140
Bimage::minimum
double minimum()
Definition: Bimage.h:477
tab
ostream & tab(ostream &out)
Definition: utilities.cpp:21
Bimage::image
Bsub_image * image
Definition: Bimage.h:181