Xmipp  v3.23.11-Nereus
wavelet.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  *
3  * Authors: Carlos Oscar S. Sorzano (coss@cnb.csic.es)
4  * Antonio Jose Rodriguez Sanchez (ajr@cnb.csic.es)
5  * Arun Kulshreshth (arun_2000_iitd@yahoo.com)
6  *
7  * Unidad de Bioinformatica of Centro Nacional de Biotecnologia , CSIC
8  *
9  * This program is free software; you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 2 of the License, or
12  * (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software
21  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
22  * 02111-1307 USA
23  *
24  * All comments concerning this program package may be sent to the
25  * e-mail address 'xmipp@cnb.csic.es'
26  ***************************************************************************/
27 /* ------------------------------------------------------------------------- */
28 /* WAVELETS */
29 /* ------------------------------------------------------------------------- */
30 
31 #include <core/bilib/wavelet.h>
32 #include <core/args.h>
33 #include <core/histogram.h>
34 #include <core/xmipp_image.h>
35 #include <core/xmipp_fftw.h>
36 
37 #include "wavelet.h"
38 #include "numerical_tools.h"
39 #include "mask.h"
40 
41 /* Wavelet ----------------------------------------------------------------- */
42 
43 void Bilib_DWT(const MultidimArray<double> &input,
44  MultidimArray<double> &result, int iterations, int isign)
45 {
46  if (iterations < 1)
47  REPORT_ERROR(ERR_INDEX_OUTOFBOUNDS, "Bilib_DWT: iterations must be >=1");
48  auto size_multiple = (int)pow(2.0, (double) iterations);
49  if (XSIZE(input) % size_multiple != 0)
51  (std::string)"Bilib_DWT: Xsize must be a multiple of " +
52  integerToString(size_multiple));
53  if (YSIZE(input) > 1 && YSIZE(input) % size_multiple != 0)
55  (std::string)"Bilib_DWT 2D: Ysize must be a multiple of " +
56  integerToString(size_multiple));
57  if (ZSIZE(input) > 1 && ZSIZE(input) % size_multiple != 0)
59  (std::string)"Bilib_DWT 3D: Zsize must be a multiple of " +
60  integerToString(size_multiple));
61 
62  result.initZeros(input);
63  TWaveletStruct TW;
64  if (isign == 1)
65  TW.Operation = "Analysis";
66  else if (isign == -1)
67  TW.Operation = "Synthesis";
68  else
69  REPORT_ERROR(ERR_VALUE_INCORRECT, (std::string)"waveletTransform: unrecognized isign");
70  TW.Filter = "Orthonormal Spline";
71  TW.BoundaryConditions = "Mirror";
72  TW.Order = "1";
73  TW.Alpha = 0;
74 
75  if (isign == 1)
76  {
77  // First iteration
78  TW.Input = MULTIDIM_ARRAY(input);
79  TW.NxOutput = TW.NxInput = XSIZE(input);
80  TW.NyOutput = TW.NyInput = YSIZE(input);
81  TW.NzOutput = TW.NzInput = ZSIZE(input);
82  TW.Output = MULTIDIM_ARRAY(result);
83  Wavelet(&TW);
84 
85  // Subsequent iterations
86  for (int i = 1; i < iterations; i++)
87  {
88  // Size of the Lowest subband
89  int xsize = XMIPP_MAX(1, XSIZE(input) / (int)pow(2.0, (double)i));
90  int ysize = XMIPP_MAX(1, YSIZE(input) / (int)pow(2.0, (double)i));
91  int zsize = XMIPP_MAX(1, ZSIZE(input) / (int)pow(2.0, (double)i));
92 
93  // Pick the Lowest subband
94  MultidimArray<double> input_aux, result_aux;
95  input_aux.resize(zsize, ysize, xsize);
96  result_aux.resize(zsize, ysize, xsize);
98  DIRECT_A3D_ELEM(input_aux, k, i, j) = DIRECT_A3D_ELEM(result, k, i, j);
99 
100  // DWT
101  TW.Input = MULTIDIM_ARRAY(input_aux);
102  TW.NxOutput = TW.NxInput = XSIZE(input_aux);
103  TW.NyOutput = TW.NyInput = YSIZE(input_aux);
104  TW.NzOutput = TW.NzInput = ZSIZE(input_aux);
105  TW.Output = MULTIDIM_ARRAY(result_aux);
106  Wavelet(&TW);
107 
108  // Return the subband to the output
110  DIRECT_A3D_ELEM(result, k, i, j) = DIRECT_A3D_ELEM(result_aux, k, i, j);
111  }
112  }
113  else if (isign == -1)
114  {
115  // Subsequent iterations
116  for (int i = iterations - 1; i >= 1; i--)
117  {
118  // Size of the Lowest subband
119  int xsize = XMIPP_MAX(1, XSIZE(input) / (int)pow(2.0, (double)i));
120  int ysize = XMIPP_MAX(1, YSIZE(input) / (int)pow(2.0, (double)i));
121  int zsize = XMIPP_MAX(1, ZSIZE(input) / (int)pow(2.0, (double)i));
122 
123  // Pick the Lowest subband
124  MultidimArray<double> input_aux, result_aux;
125  input_aux.resize(zsize, ysize, xsize);
126  result_aux.resize(zsize, ysize, xsize);
128  DIRECT_A3D_ELEM(input_aux, k, i, j) = DIRECT_A3D_ELEM(input, k, i, j);
129 
130  // DWT
131  TW.Input = MULTIDIM_ARRAY(input_aux);
132  TW.NxOutput = TW.NxInput = XSIZE(input_aux);
133  TW.NyOutput = TW.NyInput = YSIZE(input_aux);
134  TW.NzOutput = TW.NzInput = ZSIZE(input_aux);
135  TW.Output = MULTIDIM_ARRAY(result_aux);
136  Wavelet(&TW);
137 
138  // Return the subband to the output
140  DIRECT_A3D_ELEM(input, k, i, j) = DIRECT_A3D_ELEM(result_aux, k, i, j);
141  }
142 
143  // First iteration
144  TW.Input = MULTIDIM_ARRAY(input);
145  TW.NxOutput = TW.NxInput = XSIZE(input);
146  TW.NyOutput = TW.NyInput = YSIZE(input);
147  TW.NzOutput = TW.NzInput = ZSIZE(input);
148  TW.Output = MULTIDIM_ARRAY(result);
149  Wavelet(&TW);
150  }
151 }
152 
153 // Set the DWT type --------------------------------------------------------
154 void set_DWT_type(int DWT_type)
155 {
156  pwtset(DWT_type);
157 }
158 
160 {
161  DWT(v, result, -1);
162 }
163 
164 // Lowpass DWT -------------------------------------------------------------
166 {
167  MultidimArray<double> dwt, aux;
168  result.initZeros(YSIZE(v), XSIZE(v) / 2);
169  DWT(v, dwt);
170  int Nx = Get_Max_Scale(XSIZE(v));
171  for (int s = 0; s < Nx; s++)
172  {
173  // Perform the inverse DWT transform of the low pass
174  dwt.resize(XSIZE(dwt) / 2, YSIZE(dwt) / 2);
175  IDWT(dwt, aux);
176  // Copy the result to the 01 quadrant of the result
177  int x1, y1, x2, y2, x, y, i, j;
178  SelectDWTBlock(s, v, "01", x1, x2, y1, y2);
179  for (y = y1, i = 0; y <= y2; y++, i++)
180  for (x = x1, j = 0; x <= x2; x++, j++)
181  A2D_ELEM(result, y, x) = A2D_ELEM(aux, i, j);
182  }
183 }
184 
185 // Select block ------------------------------------------------------------
186 // Quadrant .---------------------------------------------------------------
187 std::string Quadrant2D(int q)
188 {
189  switch (q)
190  {
191  case 0:
192  return "00";
193  break;
194  case 1:
195  return "01";
196  break;
197  case 2:
198  return "10";
199  break;
200  case 3:
201  return "11";
202  break;
203  default:
204  REPORT_ERROR(ERR_ARG_INCORRECT,"Unknown quadrant");
205  }
206 }
207 
208 std::string Quadrant3D(int q)
209 {
210  switch (q)
211  {
212  case 0:
213  return "000";
214  break;
215  case 1:
216  return "001";
217  break;
218  case 2:
219  return "010";
220  break;
221  case 3:
222  return "011";
223  break;
224  case 4:
225  return "100";
226  break;
227  case 5:
228  return "101";
229  break;
230  case 6:
231  return "110";
232  break;
233  case 7:
234  return "111";
235  break;
236  default:
237  REPORT_ERROR(ERR_ARG_INCORRECT,"Unknown quadrant");
238  }
239 }
240 
241 // Provide block -----------------------------------------------------------
242 #define DWT_Scale(i,smax) ((int)((i==0)?smax-1:(ABS((CEIL(log10((double)(i+1))/log10(2.0))-smax)))))
243 #define DWT_Quadrant1D(i,s,smax) ((s!=smax-1)?'1':((i==0)?'0':'1'))
244 #define DWT_QuadrantnD(i,s,sp,smax) \
245  ((s!=sp)?'0':DWT_Quadrant1D(i,s,smax))
246 #define DWT_icoef1D(i,s,smax) ()
247 
248 void Get_Scale_Quadrant(int size_x, int x,
249  int &scale, std::string &quadrant)
250 {
251  double Nx = Get_Max_Scale(size_x);
252  quadrant = "x";
253  scale = DWT_Scale(x, Nx);
254  quadrant[0] = DWT_Quadrant1D(x, scale, Nx);
255 }
256 
257 void Get_Scale_Quadrant(int size_x, int size_y, int x, int y,
258  int &scale, std::string &quadrant)
259 {
260  double Nx = Get_Max_Scale(size_x);
261  double Ny = Get_Max_Scale(size_y);
262  quadrant = "xy";
263  double scalex = DWT_Scale(x, Nx);
264  double scaley = DWT_Scale(y, Ny);
265  scale = (int)(XMIPP_MIN(scalex, scaley));
266  quadrant[1] = DWT_QuadrantnD(y, scaley, scale, Ny);
267  quadrant[0] = DWT_QuadrantnD(x, scalex, scale, Nx);
268 }
269 
270 void Get_Scale_Quadrant(int size_x, int size_y, int size_z,
271  int x, int y, int z,
272  int &scale, std::string &quadrant)
273 {
274  double Nx = Get_Max_Scale(size_x);
275  double Ny = Get_Max_Scale(size_y);
276  double Nz = Get_Max_Scale(size_z);
277  quadrant = "xyz";
278  double scalex = DWT_Scale(x, Nx);
279  double scaley = DWT_Scale(y, Ny);
280  double scalez = DWT_Scale(z, Nz);
281  scale = (int)(XMIPP_MIN(scalez, XMIPP_MIN(scalex, scaley)));
282  quadrant[2] = DWT_QuadrantnD(z, scalez, scale, Nz);
283  quadrant[1] = DWT_QuadrantnD(y, scaley, scale, Ny);
284  quadrant[0] = DWT_QuadrantnD(x, scalex, scale, Nx);
285 }
286 
287 // Clean quadrant ----------------------------------------------------------
288 void clean_quadrant2D(MultidimArray<double> &I, int scale, const std::string &quadrant)
289 {
290  Matrix1D<int> corner1(2), corner2(2);
291  Matrix1D<double> r(2);
292  SelectDWTBlock(scale, I, quadrant, XX(corner1), XX(corner2), YY(corner1), YY(corner2));
293  FOR_ALL_ELEMENTS_IN_ARRAY2D_BETWEEN(corner1, corner2)
294  I(r) = 0;
295 }
296 
297 void clean_quadrant3D(MultidimArray<double> &I, int scale, const std::string &quadrant)
298 {
299  int x1, y1, z1, x2, y2, z2;
300  SelectDWTBlock(scale, I, quadrant, x1, x2, y1, y2, z1, z2);
301  Matrix1D<int> corner1(3), corner2(3);
302  Matrix1D<double> r(3);
303  SelectDWTBlock(scale, I, quadrant, XX(corner1), XX(corner2),
304  YY(corner1), YY(corner2), ZZ(corner1), ZZ(corner2));
305  FOR_ALL_ELEMENTS_IN_ARRAY3D_BETWEEN(corner1, corner2) I(r) = 0;
306 }
307 
309 {
311  if (ABS(A3D_ELEM(I, k, i, j)) > th)
312  if (A3D_ELEM(I, k, i, j) > 0)
313  A3D_ELEM(I, k, i, j) -= th;
314  else
315  A3D_ELEM(I, k, i, j) += th;
316  else
317  A3D_ELEM(I, k, i, j) = 0;
318 }
319 
320 // Adaptive soft thresholding ----------------------------------------------
322  const std::string &quadrant, double sigma)
323 {
324  // Compute block variance
325  Matrix1D<int> corner1(2), corner2(2);
326  Matrix1D<double> r(2);
327  SelectDWTBlock(scale, I, quadrant,
328  XX(corner1), XX(corner2), YY(corner1), YY(corner2));
329  double dummy, avg, stddev;
330  I.computeStats(avg, stddev, dummy, dummy, corner1, corner2);
331 
332  // Now denoise
333  double th = sigma * sigma / stddev;
334  FOR_ALL_ELEMENTS_IN_ARRAY2D_BETWEEN(corner1, corner2)
335  {
336  if (ABS(I(r)) > th)
337  if (I(r) > 0)
338  I(r) -= th;
339  else
340  I(r) += th;
341  else
342  I(r) = 0;
343  }
344 }
345 
347 {
348  // Compute histogram of the absolute values of the DWT coefficients
349  // at scale=0
350  Histogram1D hist;
351  double avg, stddev, min_val=0., max_val=0.;
352  I.computeStats(avg, stddev, min_val, max_val);
353  hist.init(0, XMIPP_MAX(ABS(min_val), ABS(max_val)), 100);
354 
355  Matrix1D<int> corner1(2), corner2(2);
356  Matrix1D<double> r(2);
357  SelectDWTBlock(0, I, "01",
358  XX(corner1), XX(corner2), YY(corner1), YY(corner2));
359  FOR_ALL_ELEMENTS_IN_ARRAY2D_BETWEEN(corner1, corner2)
360  {
361  double value=fabs(I(r));
362  INSERT_VALUE(hist,value);
363  }
364 
365  SelectDWTBlock(0, I, "10",
366  XX(corner1), XX(corner2), YY(corner1), YY(corner2));
367  FOR_ALL_ELEMENTS_IN_ARRAY2D_BETWEEN(corner1, corner2)
368  {
369  double value=fabs(I(r));
370  INSERT_VALUE(hist,value);
371  }
372 
373  SelectDWTBlock(0, I, "11",
374  XX(corner1), XX(corner2), YY(corner1), YY(corner2));
375  FOR_ALL_ELEMENTS_IN_ARRAY2D_BETWEEN(corner1, corner2)
376  {
377  double value=fabs(I(r));
378  INSERT_VALUE(hist,value);
379  }
380 
381  return hist.percentil(50) / 0.6745;
382 }
383 
385 {
386  double sigma = compute_noise_power(I);
387  for (int s = 0; s <= scale; s++)
388  {
389  adaptive_soft_thresholding_block2D(I, s, "01", sigma);
390  adaptive_soft_thresholding_block2D(I, s, "10", sigma);
391  adaptive_soft_thresholding_block2D(I, s, "11", sigma);
392  }
393 }
394 
395 // Keep central part -------------------------------------------------------
397 {
398  Mask mask(INT_MASK);
400  if (R == -1)
401  mask.R1 = (double)XSIZE(I) / 2 + 1;
402  else
403  mask.R1 = R;
404  mask.smin = 0;
405  mask.smax = Get_Max_Scale(XSIZE(I));
406  mask.quadrant = "xx";
407  mask.resize(I);
408  mask.generate_mask();
409  mask.apply_mask(I, I);
410 }
411 
412 // Bayesian Wiener filtering -----------------------------------------------
413 //DWT_Bijaoui_denoise_LL -- Bijaoui denoising at a perticular scale.
415  const std::string &orientation,
416  double mu, double S, double N)
417 {
418  Matrix1D<int> x0(2), xF(2), r(2);
419  SelectDWTBlock(scale, WI, orientation, XX(x0), XX(xF), YY(x0), YY(xF));
420 
421  double SN = S + N;
422  double S_N = S / SN;
423  if (S < 1e-6 && N < 1e-6)
424  {
426  A2D_ELEM(WI,YY(r),XX(r)) = 0;
427  }
428  else
429  {
430  double iSN=1.0/SN;
431  double iN=1.0/N;
433  {
434  double &WI_r=A2D_ELEM(WI,YY(r),XX(r));
435  double y = WI_r;
436  double ymu = y - mu;
437  double ymu2 = -0.5 * ymu * ymu;
438  double expymu2SN = exp(ymu2 * iSN);
439  double den = exp(ymu2 * iN) + expymu2SN;
440  if (den > 1e-10)
441  WI_r *= S_N * expymu2SN / den;
442  }
443  }
444 }
445 
447  const std::string &orientation,
448  double mu, double S, double N)
449 {
450  Matrix1D<int> x0(3), xF(3), r(3);
451  SelectDWTBlock(scale, WI, orientation, XX(x0), XX(xF), YY(x0), YY(xF),
452  ZZ(x0), ZZ(xF));
453 
454  double SN = S + N;
455  double S_N = S / SN;
456  if (S < 1e-6 && N < 1e-6)
457  {
459  }
460  else
461  {
463  {
464  double y = WI(r);
465  double ymu = y - mu;
466  double ymu2 = -0.5 * ymu * ymu;
467  double expymu2SN = exp(ymu2 / SN);
468  double den = exp(ymu2 / N) + expymu2SN;
469  if (den > 1e-10)
470  WI(r) = S_N * expymu2SN / den * y;
471  }
472  }
473 }
474 
475 //#define DEBUG
477  const Matrix1D<double> &power,
478  const Matrix1D<double> &Ncoefs,
479  double SNR0,
480  double SNRF,
481  double powerI,
482  double power_rest,
483  bool white_noise,
484  Matrix1D<double> &estimatedS)
485 {
486 
487  int scale_dim = power.size();
488 
490  int extra_constraints = 0;
491  if (white_noise)
492  extra_constraints += (scale_dim - 1);
493  A.initZeros(2*(scale_dim - 1) + 2*scale_dim + 2 + extra_constraints, 2*scale_dim);
494  for (int i = 1;i < scale_dim;i++)
495  {
496  A(i - 1, i - 1) = 1;
497  A(i - 1, i) = -1;
498  A(i - 1 + scale_dim - 1, i - 1 + scale_dim) = 1;
499  A(i - 1 + scale_dim - 1, i + scale_dim) = -1;
500  }
501  for (int i = 0;i < 2*scale_dim;i++)
502  A(i + 2*(scale_dim - 1), i) = -1;
503 
504  // Constraints on the SNR
505  Matrix1D<double> aux0coefs(scale_dim);
506  for (int j = 0;j < scale_dim;j++)
507  aux0coefs(j) = Ncoefs(j) * SNR0;
508  Matrix1D<double> auxFcoefs(scale_dim);
509  for (int j = 0;j < scale_dim;j++)
510  auxFcoefs(j) = Ncoefs(j) * SNRF;
511 
512  //initializing the second last row of A
513  for (int j = 0;j < scale_dim;j++)
514  A(2*(scale_dim - 1) + 2*scale_dim, j) = (-1) * auxFcoefs(j);
515  for (int j = scale_dim;j < 2*scale_dim;j++)
516  A(2*(scale_dim - 1) + 2*scale_dim, j) = Ncoefs(j - scale_dim);
517 
518  //initializing the last row of A
519  for (int j = 0;j < scale_dim;j++)
520  A(2*(scale_dim - 1) + 2*scale_dim + 1, j) = aux0coefs(j);
521  for (int j = scale_dim;j < 2*scale_dim;j++)
522  A(2*(scale_dim - 1) + 2*scale_dim + 1, j) = (-1) * Ncoefs(j - scale_dim);
523 
524  // White noise constraints
525  if (white_noise)
526  for (int i = 0; i < scale_dim - 1; i++)
527  {
528  A(A.mdimy - (scale_dim - 1) + i, i) = -1.01;
529  A(A.mdimy - (scale_dim - 1) + i, i + 1) = 1;
530  }
531 
532  //initialize the matrix b
534 
535  // Initialize Aeq matrix
536  Matrix2D<double> Aeq;
537  Aeq.initZeros(1, 2*scale_dim);
538  for (int j = 0;j < scale_dim;j++)
539  {
540  Aeq(0, j) = Ncoefs(j);
541  Aeq(0, j + scale_dim) = Ncoefs(j);
542  }
543 
544  //initialize beq matrix
545  Matrix1D<double> beq;
546  beq.initZeros(1);
547  beq(0) = powerI - power_rest;
548 
549  //initialization of Matrix C (cost matrix)
551  C.initZeros(scale_dim, 2*scale_dim);
552  for (int j = 0;j < scale_dim;j++)
553  {
554  C(j, j) = 1;
555  C(j, j + scale_dim) = 1;
556  }
557 
558  // initialise the estimatedS which will contain the solution vector
559  estimatedS.initZeros(2*scale_dim);
560 #ifdef DEBUG
561  //Writing the matrices to ASCII files for comparing with matlab
562  C.write("./matrices/C.txt");
563  power.write("./matrices/power.txt");
564  A.write("./matrices/A.txt");
565  b.write("./matrices/b.txt");
566  Aeq.write("./matrices/Aeq.txt");
567  beq.write("./matrices/beq.txt");
568 
569  std::cout << "Equation system Cx=d\n"
570  << "C=\n" << C << std::endl
571  << "d=" << (power / Ncoefs).transpose() << std::endl
572  << "Constraints\n"
573  << "Ax<=b\n"
574  << "A=\n" << A << std::endl
575  << "b=" << b.transpose() << std::endl
576  << "Aeq x=beq\n"
577  << "Aeq=\n" << Aeq << std::endl
578  << "beq=" << beq.transpose() << std::endl;
579 #endif
580 
581  // Solve the system
583  leastSquare(C, power / Ncoefs, A, b, Aeq, beq, bl, bu, estimatedS);
584  // COSS
585  estimatedS /= 2;
586 
587 #ifdef DEBUG
588 
589  std::cout << "scale_dim :: " << scale_dim << std::endl;
590  std::cout << "--------estimatedS -------- \n";
591  std::cout << estimatedS;
592  std::cout << "--------------------------- \n";
593  std::cout << "Inequality constraints agreement" << std::endl
594  << (A*estimatedS).transpose() << std::endl;
595  std::cout << "Equality constraints agreement" << std::endl
596  << (Aeq*estimatedS).transpose() << std::endl;
597  std::cout << "Goal function value: " << (C*estimatedS).transpose() << std::endl;
598 #endif
599 }
600 #undef DEBUG
601 
602 //#define DEBUG
604  double SNR0, double SNRF, bool white_noise, int tell, bool denoise)
605 {
606  /*Calculate the power of the wavelet transformed image */
607  double powerI = WI.sum2();
608 
609  /*Number of pixels and some constraints on SNR*/
610  int Xdim = XSIZE(WI);
611  int max_scale = ROUND(log(double(Xdim)) / log(2.0));
612 
613 #ifdef DEBUG
614 
615  std::cout << "powerI= " << powerI << std::endl;
616  double powerWI = WI.sum2();
617  std::cout << "powerWI= " << powerWI << std::endl;
618  std::cout << "Ydim = " << Ydim << " Xdim = " << Xdim << "\n";
619  std::cout << "Ncoef_total= " << Ncoef_total << std::endl;
620  std::cout << "max_scale = " << max_scale << "\n";
621 #endif
622 
623  /*Calculate the power at each band*/
624  //init the scale vector
625  Matrix1D<int> scale(XMIPP_MIN(allowed_scale + 1, max_scale - 1));
626  FOR_ALL_ELEMENTS_IN_MATRIX1D(scale) scale(i) = i;
627  int scale_dim = scale.size();
628 
629  //define some vectors
630  Matrix1D<double> power(scale_dim), average(scale_dim), Ncoefs(scale_dim);
631  Matrix1D<int> x0(2), xF(2), r(2);
632  std::vector<std::string> orientation;
633  orientation.push_back("01");
634  orientation.push_back("10");
635  orientation.push_back("11");
636  int orientationSize=orientation.size();
637  int jmax=scale.size();
638  for (int j = 0;j < jmax;j++)
639  {
640  for (size_t k = 0; k < orientation.size(); k++)
641  {
642  SelectDWTBlock(scale(j), WI, orientation[k],
643  XX(x0), XX(xF), YY(x0), YY(xF));
645  {
646  double aux=DIRECT_A2D_ELEM(WI,YY(r),XX(r));
647  VEC_ELEM(power,j) += aux*aux;
648  VEC_ELEM(average,j) += aux;
649  }
650  }
651  VEC_ELEM(Ncoefs,j) = (int)pow(2.0, 2 * (max_scale - VEC_ELEM(scale,j) - 1)) * orientationSize;
652  VEC_ELEM(average,j) = VEC_ELEM(average,j) / VEC_ELEM(Ncoefs,j);
653  }
654 
655  /*Evaluate the power of the unconsidered part of the image */
656  double power_rest = 0.0;
657  int Ncoefs_rest = 0;
658  SelectDWTBlock(scale(scale_dim - 1), WI, "00", XX(x0), XX(xF), YY(x0), YY(xF));
660  {
661  double aux=DIRECT_A2D_ELEM(WI,YY(r),XX(r));
662  power_rest += aux*aux;
663  }
664  Ncoefs_rest = (int)pow(2.0, 2 * (max_scale - 1 - scale(scale_dim - 1)));
665 
666  if (tell)
667  {
668  std::cout << "scale = " << std::endl << scale << std::endl;
669  std::cout << "power= " << std::endl << power << "\n";
670  std::cout << "average= " << std::endl << average << "\n";
671  std::cout << "Ncoefs= " << std::endl << Ncoefs << "\n";
672  std::cout << "power_rest= " << power_rest << "\n";
673  std::cout << "Ncoefs_rest= " << Ncoefs_rest << "\n";
674  std::cout << "powerI= " << powerI << std::endl;
675  std::cout << "Total sum of powers = " << power.sum() + power_rest << std::endl;
676  std::cout << "Difference powers = " << powerI - power.sum() - power_rest << std::endl;
677  }
678 
679  /*Solve the Equation System*/
680  Matrix1D<double> estimatedS;
682  SNR0, SNRF, powerI, power_rest, white_noise, estimatedS);
683 
684  if (tell)
685  {
686  std::cout << "estimatedS =\n" << estimatedS << std::endl;
687  double S = 0, N = 0;
688  for (int i = 0; i < scale_dim; i++)
689  {
690  N += Ncoefs(i) * estimatedS(i);
691  S += Ncoefs(i) * estimatedS(scale_dim + i);
692  }
693  std::cout << "SNR value=" << S / N << std::endl << std::endl;
694  }
695 
696  /* Apply the Bijaoui denoising to all scales >= allowed_scale */
697  if (denoise)
698  bayesian_wiener_filtering2D(WI, allowed_scale, estimatedS);
699 
700  return estimatedS;
701 }
702 #undef DEBUG
703 
705  int allowed_scale, Matrix1D<double> &estimatedS)
706 {
707  std::vector<std::string> orientation;
708  orientation.push_back("01");
709  orientation.push_back("10");
710  orientation.push_back("11");
711 
712  int max_scale = ROUND(log(double(XSIZE(WI))) / log(2.0));
713  Matrix1D<int> scale(XMIPP_MIN(allowed_scale + 1, max_scale - 1));
714  FOR_ALL_ELEMENTS_IN_MATRIX1D(scale) scale(i) = i;
715 
716  for (size_t i = 0;i < scale.size();i++)
717  {
718  double N = estimatedS(i);
719  double S = estimatedS(i + scale.size());
720  for (size_t k = 0; k < orientation.size(); k++)
721  DWT_Bijaoui_denoise_LL2D(WI, scale(i), orientation[k], 0, S, N);
722  }
723 }
724 
725 //#define DEBUG
727  double SNR0, double SNRF, bool white_noise,
728  int tell, bool denoise)
729 {
730  /*Calculate the power of the wavelet transformed image */
731  double powerI = WI.sum2();
732 
733  /*Number of pixels and some constraints on SNR*/
734  size_t Xdim=ZSIZE(WI);
735  int max_scale = ROUND(log(double(Xdim)) / log(2.0));
736 
737 #ifdef DEBUG
738 
739  std::cout << "powerI= " << powerI << std::endl;
740  double powerWI = WI.sum2();
741  std::cout << "powerWI= " << powerWI << std::endl;
742  std::cout << "Zdim= " << Zdim << " Ydim = " << Ydim << " Xdim = " << Xdim << "\n";
743  std::cout << "Ncoef_total= " << Ncoef_total << std::endl;
744  std::cout << "max_scale = " << max_scale << "\n";
745 #endif
746 
747  /*Calculate the power at each band*/
748  //init the scale vector
749  Matrix1D<int> scale(allowed_scale + 1);
750  FOR_ALL_ELEMENTS_IN_MATRIX1D(scale) scale(i) = i;
751  int scale_dim = scale.size();
752 
753  //define some vectors
754  Matrix1D<double> power(scale_dim), average(scale_dim), Ncoefs(scale_dim);
755  Matrix1D<int> x0(3), xF(3), r(3);
756  std::vector<std::string> orientation;
757  orientation.push_back("001");
758  orientation.push_back("010");
759  orientation.push_back("011");
760  orientation.push_back("100");
761  orientation.push_back("101");
762  orientation.push_back("110");
763  orientation.push_back("111");
764  for (size_t j = 0;j < scale.size();j++)
765  {
766  for (size_t k = 0; k < orientation.size(); k++)
767  {
768  SelectDWTBlock(scale(j), WI, orientation[k],
769  XX(x0), XX(xF), YY(x0), YY(xF), ZZ(x0), ZZ(xF));
771  {
772  power(j) += WI(r) * WI(r);
773  average(j) += WI(r);
774  }
775  }
776  Ncoefs(j) = (int)pow(2.0, 3 * (max_scale - scale(j) - 1)) * orientation.size();
777  average(j) = average(j) / Ncoefs(j);
778  }
779 
780  /*Evaluate the power of the unconsidered part of the image */
781  double power_rest = 0.0;
782  int Ncoefs_rest = 0;
783  SelectDWTBlock(scale(scale_dim - 1), WI, "000", XX(x0), XX(xF), YY(x0), YY(xF),
784  ZZ(x0), ZZ(xF));
786  power_rest += WI(r) * WI(r);
787  Ncoefs_rest = (int)pow(2.0, 3 * (max_scale - 1 - scale(scale_dim - 1)));
788 
789  if (tell)
790  {
791  std::cout << "scale = " << std::endl << scale << std::endl;
792  std::cout << "power= " << std::endl << power << "\n";
793  std::cout << "average= " << std::endl << average << "\n";
794  std::cout << "Ncoefs= " << std::endl << Ncoefs << "\n";
795  std::cout << "power_rest= " << power_rest << "\n";
796  std::cout << "Ncoefs_rest= " << Ncoefs_rest << "\n";
797  std::cout << "powerI= " << powerI << std::endl;
798  std::cout << "Total sum of powers = " << power.sum() + power_rest << std::endl;
799  std::cout << "Difference powers = " << powerI - power.sum() - power_rest << std::endl;
800  }
801 
802  /*Solve the Equation System*/
803  Matrix1D<double> estimatedS;
805  SNR0, SNRF, powerI, power_rest, white_noise, estimatedS);
806  if (tell)
807  {
808  std::cout << "estimatedS =\n" << estimatedS << std::endl;
809  double S = 0, N = 0;
810  for (int i = 0; i < scale_dim; i++)
811  {
812  N += Ncoefs(i) * estimatedS(i);
813  S += Ncoefs(i) * estimatedS(scale_dim + i);
814  }
815  std::cout << "SNR value=" << S / N << std::endl << std::endl;
816  }
817 
818  /* Apply the Bijaoui denoising to all scales >= allowed_scale */
819  if (denoise)
820  bayesian_wiener_filtering3D(WI, allowed_scale, estimatedS);
821  return estimatedS;
822 }
823 #undef DEBUG
824 
826  int allowed_scale, Matrix1D<double> &estimatedS)
827 {
828  std::vector<std::string> orientation;
829  orientation.push_back("001");
830  orientation.push_back("010");
831  orientation.push_back("011");
832  orientation.push_back("100");
833  orientation.push_back("101");
834  orientation.push_back("110");
835  orientation.push_back("111");
836 
837  int max_scale = ROUND(log(double(XSIZE(WI))) / log(2.0));
838  MultidimArray<int> scale(XMIPP_MIN(allowed_scale + 1, max_scale - 1));
839  FOR_ALL_ELEMENTS_IN_ARRAY1D(scale) scale(i) = i;
840 
841  for (size_t i = 0;i < XSIZE(scale);i++)
842  {
843  double N = estimatedS(i);
844  double S = estimatedS(i + XSIZE(scale));
845  for (size_t k = 0; k < orientation.size(); k++)
846  DWT_Bijaoui_denoise_LL3D(WI, scale(i), orientation[k], 0, S, N);
847  }
848 }
849 
853  MultidimArray< double >& Energy,
854  MultidimArray<double>& lowPass,
855  MultidimArray<double>& Radius,
856  MultidimArray< std::complex <double> >& H,
857  int nScale,
858  double minWaveLength,
859  double mult,
860  double sigmaOnf)
861 {
862 
863 // #define DEBUG
864  double epsilon= .0001; // Used to prevent division by zero.
865  //First we set the image origin in the image center
866  I.setXmippOrigin();
867  //Image size
868  size_t NR, NC,NZ, NDim;
869  I.getDimensions(NC,NR,NZ,NDim);
870 
871  if ( (NZ!=1) || (NDim!=1) )
872  REPORT_ERROR(ERR_MULTIDIM_DIM,(std::string)"ZDim and NDim has to be equals to one");
873 
875  // Fourier Transformer
876  FourierTransformer ftrans(FFTW_BACKWARD);//, ftransh(FFTW_BACKWARD), ftransf(FFTW_BACKWARD);
877  ftrans.FourierTransform(I, fftIm, false);
878 
879  if ( (lowPass.xinit == 0) & (lowPass.yinit == 0) & (Radius.xinit == 0) & (Radius.yinit == 0)
880  & (H.xinit == 0) & (H.yinit == 0) )
881  {
882 
883  H.resizeNoCopy(I);
884  lowPass.resizeNoCopy(I);
885  Radius.resizeNoCopy(I);
886 
887  double cutoff = .4;
888  double n = 10;
889  double wx,wy;
890 
891  for (int i=STARTINGY(I); i<=FINISHINGY(I); ++i)
892  {
893  FFT_IDX2DIGFREQ(i,YSIZE(I),wy);
894  double wy2=wy*wy;
895  for (int j=STARTINGX(I); j<=FINISHINGX(I); ++j)
896  {
897  FFT_IDX2DIGFREQ(j,XSIZE(I),wx);
898 
899  double wx2=wx*wx;
900  double radius=sqrt(wy2+wx2);
901  if (radius < 1e-10) radius=1;
902  A2D_ELEM(Radius,i,j)=radius;
903  auto *ptr=(double*)&A2D_ELEM(H,i,j);
904  *ptr=wy/radius;
905  *(ptr+1)=wx/radius;
906  A2D_ELEM(lowPass,i,j)= 1.0/(1.0+std::pow(radius/cutoff,n));
907  }
908 
909  }
910 
911  }
912 
913  MultidimArray<double> logGabor;
914  logGabor.resizeNoCopy(I);
915  //Bandpassed image in the frequency domain and in the spatial domain.
916  //h is a Bandpassed monogenic filtering, real part of h contains
917  //convolution result with h1, imaginary part
918  //contains convolution result with h2.
919  MultidimArray< std::complex <double> > fftImF, fullFftIm, f,Hc,h;
920 
921  fftImF.resizeNoCopy(I);
922  Hc.resizeNoCopy(I);
923  f.resizeNoCopy(I);
924  h.resizeNoCopy(I);
925 
926  MultidimArray<double> An,AnTemp;
931  MultidimArray<double> tempMat;
932 
933  temp.resizeNoCopy(I);
934  An.resizeNoCopy(I);
935  F.resizeNoCopy(I);
936  h1.resizeNoCopy(I);
937  h2.resizeNoCopy(I);
938  AnTemp.resizeNoCopy(I);
939  ftrans.getCompleteFourier(fullFftIm);
940  CenterFFT(fullFftIm,false);
941 
942  for (int num = 0; num < nScale; ++num)
943  {
944  double waveLength = minWaveLength;
945 
946  for(int numMult=0; numMult < num;numMult++)
947  waveLength*=mult;
948 
949  double fo = 1.0/waveLength;
950  FOR_ALL_ELEMENTS_IN_ARRAY2D(fullFftIm)
951  {
952  double temp1 =(std::log(A2D_ELEM(Radius,i,j)/fo));
953  double temp2 = std::log(sigmaOnf);
954  A2D_ELEM(logGabor,i,j) = std::exp(-(temp1*temp1) /(2 * temp2*temp2))*A2D_ELEM(lowPass,i,j);
955  if (A2D_ELEM(Radius,i,j)<=1e-10) (A2D_ELEM(logGabor,i,j)=0);
956 
957  auto *ptr= (double*)&A2D_ELEM(fullFftIm,i,j);
958  temp1 = *ptr;
959  temp2 = *(ptr+1);
960  ptr= (double*)&A2D_ELEM(fftImF,i,j);
961  *ptr=temp1*A2D_ELEM(logGabor,i,j);
962  *(ptr+1)=temp2*A2D_ELEM(logGabor,i,j);
963  }
964 
965  CenterFFT(fftImF,true);
966  Hc = fftImF*H;
967  ftrans.inverseFourierTransform(fftImF,f);
968  ftrans.inverseFourierTransform(Hc,h);
969 
970  //ftransf.setFourier(fftImF);
971  //ftransf.inverseFourierTransform();
972  //ftransh.setFourier(Hc);
973  //ftransh.inverseFourierTransform();
974 
975  f.getReal(temp);
976  F += temp;
977  AnTemp = temp*temp;
978 
979  h.getReal(temp);
980  h1 += temp;
981  AnTemp += temp*temp;
982 
983  h.getImag(temp);
984  h2 += temp;
985  AnTemp += temp*temp;
986 
987  AnTemp.selfSQRT();
988  An += AnTemp;
989  }
990 
991  Or.resizeNoCopy(I);
992  Or.setXmippOrigin();
993 
994  Ph.resizeNoCopy(I);
995  Ph.setXmippOrigin();
996 
997  Energy.resizeNoCopy(I);
998  Energy.setXmippOrigin();
999 
1001  {
1002  double temph1 = A2D_ELEM(h1,i,j);
1003  double temph2 = A2D_ELEM(h2,i,j);
1004  double tempF = A2D_ELEM(F,i,j);
1005 
1006  A2D_ELEM(Or,i,j) = std::atan2(temph1,temph2);
1007  A2D_ELEM(Ph,i,j)= std::atan2(tempF, std::sqrt(temph1*temph1+
1008  temph2*temph2));
1009  A2D_ELEM(Energy,i,j) = std::sqrt(tempF*tempF+temph1*temph1
1010  + temph2*temph2)+epsilon;
1011  }
1012 
1013 #ifdef DEBUG
1014 
1015  FileName fpName1 = "test1.txt";
1016  FileName fpName2 = "test2.txt";
1017  FileName fpName3 = "test3.txt";
1018  FileName fpName4 = "test4.txt";
1019 
1020  Or.write(fpName1);
1021  Ph.write(fpName2);
1022  Energy.write(fpName3);
1023 
1024  #endif
1025 }
void phaseCongMono(MultidimArray< double > &I, MultidimArray< double > &Ph, MultidimArray< double > &Or, MultidimArray< double > &Energy, MultidimArray< double > &lowPass, MultidimArray< double > &Radius, MultidimArray< std::complex< double > > &H, int nScale, double minWaveLength, double mult, double sigmaOnf)
Definition: wavelet.cpp:850
Index out of bounds.
Definition: xmipp_error.h:132
#define MAT_YSIZE(m)
Definition: matrix2d.h:124
long NzInput
Definition: wavelet.h:37
#define YSIZE(v)
#define A2D_ELEM(v, i, j)
#define VEC_ELEM(v, i)
Definition: matrix1d.h:245
void Bilib_DWT(const MultidimArray< double > &input, MultidimArray< double > &result, int iterations, int isign)
Definition: wavelet.cpp:43
void set_DWT_type(int DWT_type)
Definition: wavelet.cpp:154
void resize(size_t Ndim, size_t Zdim, size_t Ydim, size_t Xdim, bool copy=true)
#define XMIPP_MAX(x, y)
Definition: xmipp_macros.h:193
int Get_Max_Scale(int size)
Definition: wavelet.h:71
int smin
Definition: mask.h:474
void inverseFourierTransform()
Definition: xmipp_fftw.cpp:329
#define FINISHINGX(v)
#define REPORT_ERROR(nerr, ErrormMsg)
Definition: xmipp_error.h:211
size_t size() const
Definition: matrix1d.h:508
double * Input
Definition: wavelet.h:31
void DWT_lowpass2D(const MultidimArray< double > &v, MultidimArray< double > &result)
Definition: wavelet.cpp:165
#define INSERT_VALUE(histogram, value)
Definition: histogram.h:205
double * bl
void resizeNoCopy(const MultidimArray< T1 > &v)
Definition: mask.h:360
int smax
Definition: mask.h:478
void sqrt(Image< double > &op)
void clean_quadrant3D(MultidimArray< double > &I, int scale, const std::string &quadrant)
Definition: wavelet.cpp:297
void computeStats(double &avg, double &stddev, T &minval, T &maxval) const
static double * y
#define DIRECT_A2D_ELEM(v, i, j)
#define MULTIDIM_ARRAY(v)
void resize(size_t Xdim)
Definition: mask.cpp:654
double percentil(double percent_mass)
Definition: histogram.cpp:160
void bayesian_solve_eq_system(const Matrix1D< double > &power, const Matrix1D< double > &Ncoefs, double SNR0, double SNRF, double powerI, double power_rest, bool white_noise, Matrix1D< double > &estimatedS)
Definition: wavelet.cpp:476
String integerToString(int I, int _width, char fill_with)
#define FOR_ALL_DIRECT_ELEMENTS_IN_ARRAY3D(V)
Incorrect MultidimArray size.
Definition: xmipp_error.h:174
void adaptive_soft_thresholding_block2D(MultidimArray< double > &I, int scale, const std::string &quadrant, double sigma)
Definition: wavelet.cpp:321
const char * Filter
Definition: wavelet.h:52
void write(const FileName &fn) const
Definition: matrix1d.cpp:794
i<=ncnstr;i++) cs[i].mult=0.e0;if(nfsip) for(i=1;i<=nob;i++) { ob[i].mult=0.e0;ob[i].mult_L=0.e0;} for(i=1;i<=nqpram;i++) { ii=k+i;if(clamda[ii]==0.e0 &&clamda[ii+nqpram]==0.e0) continue;else if(clamda[ii] !=0.e0) clamda[ii]=-clamda[ii];else clamda[ii]=clamda[ii+nqpram];} nqnp=nqpram+ncnstr;for(i=1;i<=nqpram;i++) param-> mult[i]
#define STARTINGX(v)
void init(double min_val, double max_val, int n_steps)
Definition: histogram.cpp:71
doublereal * x
#define i
ql0001_ & k(htemp+1),(cvec+1),(atemp+1),(bj+1),(bl+1),(bu+1),(x+1),(clamda+1), &iout, infoqp, &zero,(w+1), &lenw,(iw+1), &leniw, &glob_grd.epsmac
#define FOR_ALL_ELEMENTS_IN_ARRAY2D(m)
Matrix1D< T > transpose() const
Definition: matrix1d.cpp:644
void clean_quadrant2D(MultidimArray< double > &I, int scale, const std::string &quadrant)
Definition: wavelet.cpp:288
double temp2
#define STARTINGY(v)
Matrix1D< double > bayesian_wiener_filtering2D(MultidimArray< double > &WI, int allowed_scale, double SNR0, double SNRF, bool white_noise, int tell, bool denoise)
Definition: wavelet.cpp:603
void CenterFFT(MultidimArray< T > &v, bool forward)
Definition: xmipp_fft.h:291
#define A3D_ELEM(V, k, i, j)
double * bu
#define DWT_Quadrant1D(i, s, smax)
Definition: wavelet.cpp:243
double compute_noise_power(MultidimArray< double > &I)
Definition: wavelet.cpp:346
#define FOR_ALL_ELEMENTS_IN_MATRIX1D(v)
Definition: matrix1d.h:72
void apply_mask(const MultidimArray< T > &I, MultidimArray< T > &result, T subs_val=0, bool apply_geo=false)
Definition: mask.h:635
#define FOR_ALL_ELEMENTS_IN_ARRAY3D(V)
doublereal * b
std::string Quadrant3D(int q)
Definition: wavelet.cpp:208
void log(Image< double > &op)
void DWT_Bijaoui_denoise_LL2D(MultidimArray< double > &WI, int scale, const std::string &orientation, double mu, double S, double N)
Definition: wavelet.cpp:414
#define x0
#define XX(v)
Definition: matrix1d.h:85
void transpose(double *array, int size)
void getCompleteFourier(T &V)
Definition: xmipp_fftw.h:234
double * f
double * Output
Definition: wavelet.h:39
const char * Operation
Definition: wavelet.h:47
void DWT(const MultidimArray< T > &v, MultidimArray< double > &result, int isign=1)
Definition: wavelet.h:83
Incorrect argument received.
Definition: xmipp_error.h:113
#define DWT_QuadrantnD(i, s, sp, smax)
Definition: wavelet.cpp:244
double R1
Definition: mask.h:413
#define XSIZE(v)
void write(const FileName &fn) const
long NzOutput
Definition: wavelet.h:45
#define DWT_Scale(i, smax)
Definition: wavelet.cpp:242
void adaptive_soft_thresholding2D(MultidimArray< double > &I, int scale)
Definition: wavelet.cpp:384
int type
Definition: mask.h:402
#define ABS(x)
Definition: xmipp_macros.h:142
#define ZSIZE(v)
double z
#define ROUND(x)
Definition: xmipp_macros.h:210
double sum(bool average=false) const
Definition: matrix1d.cpp:652
std::string quadrant
Definition: mask.h:483
size_t mdimy
Definition: matrix2d.h:413
double dummy
long NyInput
Definition: wavelet.h:35
int Wavelet(struct TWaveletStruct *Data)
#define xF
void initZeros()
Definition: matrix1d.h:592
#define DIRECT_A3D_ELEM(v, k, i, j)
#define BINARY_DWT_CIRCULAR_MASK
Definition: mask.h:377
void FourierTransform(T &v, T1 &V, bool getCopy=true)
Definition: xmipp_fftw.h:166
__device__ float FFT_IDX2DIGFREQ(int idx, int size)
#define XMIPP_MIN(x, y)
Definition: xmipp_macros.h:181
#define j
#define YY(v)
Definition: matrix1d.h:93
void power(Image< double > &op)
double sum2() const
#define FINISHINGY(v)
#define FOR_ALL_ELEMENTS_IN_ARRAY1D(v)
void SelectDWTBlock(int scale, const MultidimArray< T > &I, const std::string &quadrant, int &x1, int &x2)
Definition: wavelet.h:134
void generate_mask(bool apply_geo=false)
Definition: mask.cpp:1577
void getReal(MultidimArray< double > &realImg) const
Matrix1D< double > bayesian_wiener_filtering3D(MultidimArray< double > &WI, int allowed_scale, double SNR0, double SNRF, bool white_noise, int tell, bool denoise)
Definition: wavelet.cpp:726
double Alpha
Definition: wavelet.h:58
void pwtset(int n)
void write(const FileName &fn) const
Definition: matrix2d.cpp:113
#define INT_MASK
Definition: mask.h:385
std::string Quadrant2D(int q)
Definition: wavelet.cpp:187
void initZeros()
Definition: matrix2d.h:626
const char * BoundaryConditions
Definition: wavelet.h:54
int mu
void DWT_keep_central_part(MultidimArray< double > &I, double R)
Definition: wavelet.cpp:396
void IDWT(const MultidimArray< double > &v, MultidimArray< double > &result)
Definition: wavelet.cpp:159
long NxOutput
Definition: wavelet.h:41
void soft_thresholding(MultidimArray< double > &I, double th)
Definition: wavelet.cpp:308
Incorrect MultidimArray dimensions.
Definition: xmipp_error.h:173
#define FOR_ALL_ELEMENTS_IN_ARRAY2D_BETWEEN(corner1, corner2)
long NxInput
Definition: wavelet.h:33
void initZeros(const MultidimArray< T1 > &op)
void getImag(MultidimArray< double > &imagImg) const
void DWT_Bijaoui_denoise_LL3D(MultidimArray< double > &WI, int scale, const std::string &orientation, double mu, double S, double N)
Definition: wavelet.cpp:446
double epsilon
Incorrect value received.
Definition: xmipp_error.h:195
int * n
#define ZZ(v)
Definition: matrix1d.h:101
long NyOutput
Definition: wavelet.h:43
const char * Order
Definition: wavelet.h:56
#define FOR_ALL_ELEMENTS_IN_ARRAY3D_BETWEEN(corner1, corner2)
double temp1
void leastSquare(const Matrix2D< double > &C, const Matrix1D< double > &d, const Matrix2D< double > &A, const Matrix1D< double > &b, const Matrix2D< double > &Aeq, const Matrix1D< double > &beq, Matrix1D< double > &bl, Matrix1D< double > &bu, Matrix1D< double > &x)
void Get_Scale_Quadrant(int size_x, int x, int &scale, std::string &quadrant)
Definition: wavelet.cpp:248
void getDimensions(size_t &Xdim, size_t &Ydim, size_t &Zdim, size_t &Ndim) const