Xmipp  v3.23.11-Nereus
program_image_ssnr.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  * Authors: Carlos Oscar S. Sorzano (coss@cnb.csic.es)
3  *
4  *
5  * Unidad de Bioinformatica of Centro Nacional de Biotecnologia , CSIC
6  *
7  * This program is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 2 of the License, or
10  * (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
20  * 02111-1307 USA
21  *
22  * All comments concerning this program package may be sent to the
23  * e-mail address 'xmipp@cnb.csic.es'
24  ***************************************************************************/
25 
26 #include <algorithm>
27 #include "program_image_ssnr.h"
28 #include "data/mask.h"
29 #include "core/xmipp_fftw.h"
31 
33 {
34  produces_a_metadata = true;
36  keep_input_columns = true;
37  remove_disabled = false;
38  addUsageLine("Analyze image SSNR. For doing so, we estimate the SSNR of each particle defining as signal "\
39  "the part of the image within a certain radius, and as noise the part of the image outside.");
41  addParamsLine(" [-R <r=-1>]: Particle radius, by default, half size of the image");
42  addParamsLine(" [--Rwidth <r=3>]: Transition radius the mask is 1 till R-Rwidth, and zero from R+Rwidth");
43  addParamsLine(" [--fmin <f=40>]: Minimum frequency (in Angstroms) to measure");
44  addParamsLine(" [--fmax <f=3>]: Maximum frequency (in Angstroms) to measure");
45  addParamsLine(" [--sampling <Ts=1>]: Sampling rate in Angstroms/pixel");
46  addParamsLine(" [--ssnrcut <ssnr=-1>]: Disable images whose SSNR is below this value");
47  addParamsLine(" [--ssnrpercent <p=-1>]: Disable images whose SSNR is below this percentage");
48  addParamsLine(" [--normalizessnr]: Normalize the SSNR by dividing by the maximum SSNR");
49  addExampleLine("xmipp_image_ssnr -i images.xmd -o imagesOut.xmd ");
50 }
51 
53 {
55  R=getDoubleParam("-R");
56  Rwidth=getDoubleParam("--Rwidth");
57  fmin=getDoubleParam("--fmin");
58  fmax=getDoubleParam("--fmax");
59  sampling=getDoubleParam("--sampling");
60  ssnrcut=getDoubleParam("--ssnrcut");
61  ssnrpercent=getDoubleParam("--ssnrpercent");
62  normalizessnr=checkParam("--normalizessnr");
63 }
64 
66 {
67  size_t Xdim, Ydim, Zdim, Ndim;
68  getImageSize(*getInputMd(), Xdim, Ydim, Zdim, Ndim);
69  maskS.initZeros(Ydim,Xdim);
71 
72  if (R==-1)
73  R=0.5*Xdim-Rwidth;
74  RaisedCosineMask(maskS,R-Rwidth,R+Rwidth);
75  maskN=1-maskS;
76 
77  imin=(size_t)std::max(3.0,0.5*Xdim*(sampling/fmin));
78  imax=(size_t)std::min(Xdim-3.0,0.5*Xdim*(sampling/fmax));
79 }
80 
81 void ProgImageSSNR::processImage(const FileName &fnImg, const FileName &fnImgOut, const MDRow &rowIn, MDRow &rowOut)
82 {
83  // Copy Enabled
84  int enabled;
85  rowIn.getValue(MDL_ENABLED,enabled);
86  rowOut.setValue(MDL_ENABLED,enabled);
87 
88  img.read(fnImg);
89  img().setXmippOrigin();
90 
91  imgN()=imgS()=img();
92  imgS()*=maskS;
93  imgN()*=maskN;
94 
97 
98  double SSNR=0;
100  {
101  if (i>=imin && i<=imax)
102  {
103  double S=DIRECT_A1D_ELEM(spectrumS,i);
104  double N=DIRECT_A1D_ELEM(spectrumN,i);
105  if (S>0 && N>0)
106  SSNR+=log10(S)-log10(N);
107  }
108  }
109  SSNR*=10.0/(imax-imin+1); // decibels
110  rowOut.setValue(MDL_CUMULATIVE_SSNR,SSNR);
111 
112  //spectrumS.write("PPPS.txt");
113  //spectrumN.write("PPPN.txt");
114  //std::cout << fnImg << " SSNR=" << SSNR << std::endl;
115  //std::cout << "Press any key\n";
116  // char c; std::cin>> c;
117 }
118 
119 void thresholdSSNR(MetaData &mdOut, double ssnrcut)
120 {
121  for (size_t objId : mdOut.ids())
122  {
123  double ssnr;
124  mdOut.getValue(MDL_CUMULATIVE_SSNR,ssnr,objId);
125  if (ssnr<ssnrcut)
126  mdOut.setValue(MDL_ENABLED,-1,objId);
127  }
128 }
129 
131 {
132  double maxSSNR=-1e38;
133  for (size_t objId : mdOut.ids())
134  {
135  double ssnr;
136  mdOut.getValue(MDL_CUMULATIVE_SSNR,ssnr,objId);
137  if (ssnr>maxSSNR)
138  maxSSNR=ssnr;
139  }
140 
141  if (maxSSNR>0)
142  {
143  double imaxSSNR=1/maxSSNR;
144  for (size_t objId : mdOut.ids())
145  {
146  double ssnr;
147  mdOut.getValue(MDL_CUMULATIVE_SSNR,ssnr,objId);
148  mdOut.setValue(MDL_WEIGHT_SSNR,ssnr*imaxSSNR,objId);
149  }
150  }
151 }
152 
154 {
155  if (ssnrcut>0)
157 
158  if (ssnrpercent>0)
159  {
160  std::vector<double> ssnr;
162  std::sort(ssnr.begin(),ssnr.end());
163  auto idx=(size_t)(ssnrpercent/100.0*ssnr.size());
164  thresholdSSNR(getOutputMd(),ssnr[idx]);
165  }
166 
167  if (normalizessnr)
169  if (fn_out!="")
171  else
173 }
void thresholdSSNR(MetaData &mdOut, double ssnrcut)
void min(Image< double > &op1, const Image< double > &op2)
Image< double > imgS
double getDoubleParam(const char *param, int arg=0)
void normalizeSSNR(MetaData &mdOut)
void getImageSize(const MetaData &md, size_t &Xdim, size_t &Ydim, size_t &Zdim, size_t &Ndim, MDLabel image_label)
void write(const FileName &outFile, WriteModeMetaData mode=MD_OVERWRITE) const
Image< double > imgN
virtual IdIteratorProxy< false > ids()
#define FOR_ALL_DIRECT_ELEMENTS_IN_ARRAY1D(v)
MultidimArray< double > maskS
virtual bool getValue(MDObject &mdValueOut, size_t id) const =0
#define i
Is this image enabled? (int [-1 or 1])
void getSpectrum(MultidimArray< double > &Min, MultidimArray< double > &spectrum, int spectrum_type)
Definition: xmipp_fftw.cpp:752
#define DIRECT_A1D_ELEM(v, i)
T & getValue(MDLabel label)
FileName fn_in
Filenames of input and output Metadata.
void max(Image< double > &op1, const Image< double > &op2)
void addExampleLine(const char *example, bool verbatim=true)
void log10(Image< double > &op)
void processImage(const FileName &fnImg, const FileName &fnImgOut, const MDRow &rowIn, MDRow &rowOut)
void sort(struct DCEL_T *dcel)
Definition: sorting.cpp:18
Cumulative SSNR (double)
Weight due to SSNR.
bool setValue(const MDLabel label, const T &valueIn, size_t id)
bool remove_disabled
Remove disabled images from the input selfile.
void getColumnValues(const MDLabel label, std::vector< MDObject > &valuesOut) const override
void setValue(MDLabel label, const T &d, bool addLabel=true)
#define POWER_SPECTRUM
Definition: xmipp_fftw.h:668
MultidimArray< double > maskN
bool keep_input_columns
Keep input metadata columns.
bool checkParam(const char *param)
int read(const FileName &name, DataMode datamode=DATA, size_t select_img=ALL_IMAGES, bool mapData=false, int mode=WRITE_READONLY)
bool each_image_produces_an_output
Indicate that an output is produced for each image in the input.
void addUsageLine(const char *line, bool verbatim=false)
void initZeros(const MultidimArray< T1 > &op)
Image< double > img
void RaisedCosineMask(MultidimArray< double > &mask, double r1, double r2, int mode, double x0, double y0, double z0)
Definition: mask.cpp:36
MultidimArray< double > spectrumN
MultidimArray< double > spectrumS
bool produces_a_metadata
Indicate that the unique final output file is a Metadata.
void addParamsLine(const String &line)