ImgAlgos/include/AlgSmearing.h

Go to the documentation of this file.
00001 #ifndef IMGALGOS_ALGSMEARING_H
00002 #define IMGALGOS_ALGSMEARING_H
00003 
00004 //--------------------------------------------------------------------------
00005 // File and Version Information:
00006 //      $Id: AlgSmearing.h 9478 2015-01-13 20:07:05Z dubrovin@SLAC.STANFORD.EDU $
00007 //
00008 // Description: see documentation below
00009 //
00010 //------------------------------------------------------------------------
00011 
00012 //-----------------
00013 // C/C++ Headers --
00014 //-----------------
00015 
00016 #include <string>
00017 #include <iostream> // for cout
00018 #include <cstddef>  // for size_t
00019 #include <cstring>  // for memcpy
00020 
00021 using namespace std;
00022 
00023 //----------------------
00024 // Base Class Headers --
00025 //----------------------
00026 
00027 
00028 //-------------------------------
00029 // Collaborating Class Headers --
00030 //-------------------------------
00031 
00032 #include "MsgLogger/MsgLogger.h"
00033 #include "ndarray/ndarray.h"
00034 
00035 //------------------------------------
00036 // Collaborating Class Declarations --
00037 //------------------------------------
00038 
00039 //              ---------------------
00040 //              -- Class Interface --
00041 //              ---------------------
00042 
00043 namespace ImgAlgos {
00044 
00045 /// @addtogroup ImgAlgos
00046 
00047 /**
00048  *  @ingroup ImgAlgos
00049  *
00050  *  @brief AlgSmearing - is a smearing algorithm for ndarray<T,2> using 2-d Gaussian weights.
00051  *
00052  *  This software was developed for the LCLS project.  If you use all or 
00053  *  part of it, please give an appropriate acknowledgment.
00054  *
00055  *  @version $Id: AlgSmearing.h 9478 2015-01-13 20:07:05Z dubrovin@SLAC.STANFORD.EDU $
00056  *
00057  *  @author Mikhail S. Dubrovin
00058  *
00059  *  @see AlgSmearing
00060  *
00061  *
00062  *  @anchor interface
00063  *  @par<interface> Interface Description
00064  *
00065  *
00066  * 
00067  *  @li  Include
00068  *  @code
00069  *  #include "ImgAlgos/AlgSmearing.h"
00070  *  #include "ndarray/ndarray.h"     // need it for I/O arrays
00071  *  @endcode
00072  *
00073  *
00074  *
00075  *  @li Initialization
00076  *  \n
00077  *  @code
00078  *  double      sigma    = 2.5;
00079  *  int         nsm      = 3;
00080  *  double      thr_low  = 10;
00081  *  unsigned    opt      = 1;
00082  *  unsigned    pbits    = 0177777;
00083  *  size_t      seg      = 2;
00084  *  size_t      rowmin   = 10;
00085  *  size_t      rowmax   = 170;
00086  *  size_t      colmin   = 100;
00087  *  size_t      colmax   = 200;
00088  *  double      value    = 0;
00089  * 
00090  *  AlgSmearing* p_sm = new AlgSmearing( sigma, nsm, thr_low, opt, pbits,
00091  *                                       seg, rowmin, rowmax, colmin, colmax, value );
00092  *  @endcode
00093  *
00094  *
00095  *
00096  *  @li Do smearing
00097  *  @code
00098  *  ndarray<const T,2> nda_raw = ....;    // input raw ndarray
00099  *  ndarray<T,2> nda_sme(shape);          // output smeared ndarray
00100  *
00101  *  p_sm->smearing<T>(nda_raw, nda_sme);  // do smearing of input  ndarray<const T,2> nda_raw to output nda_sme
00102  *  @endcode
00103  *
00104  *
00105  *
00106  *  @li Access methods
00107  *  @code
00108  *  const size_t seg = p_sm->segind();
00109  *  @endcode
00110  *
00111  *
00112  *
00113  *  @li Print methods
00114  *  @code
00115  *  p_sm->printInputPars();
00116  *  p_sm->printWeights();
00117  *  @endcode
00118  */
00119 
00120 //template <typename T>
00121 class AlgSmearing  {
00122 public:
00123 
00124   //static const size_t RSMMAX = 10;
00125 
00126   /**
00127    * @brief Class constructor is used for initialization of all paramaters. 
00128    * 
00129    * @param[in] sigma - smearing width parameter to generate the matrix of weights
00130    * @param[in] nsm   - (radial) number of neighbour rows and columns around pixel involved in smearing 
00131    * @param[in] thr_low - threshold on intensity; pixels with intensity above this threshold are accounted in smearing
00132    * @param[in] opt - pre-fill options for output array outside window region; 0-fill by zeros, 1-copy raw, 2-do nothing
00133    * @param[in] pbits  - print control bit-word; =0-print nothing, +1-input parameters, +2-matrix of weights, +128-detail at smearing.
00134    * @param[in] seg    - ROI segment index in the ndarray
00135    * @param[in] rowmin - ROI window limit
00136    * @param[in] rowmax - ROI window limit
00137    * @param[in] colmin - ROI window limit
00138    * @param[in] colmax - ROI window limit
00139    * @param[in] value  - pre-fill value 
00140    */
00141 
00142   AlgSmearing ( const double&   sigma   = 2
00143               , const int&      nsm     = 5
00144               , const double&   thr_low = -1e10
00145               , const unsigned& opt     = 1
00146               , const unsigned& pbits   = 0
00147               , const size_t&   seg     = -1
00148               , const size_t&   rowmin  = 0
00149               , const size_t&   rowmax  = 1e6
00150               , const size_t&   colmin  = 0
00151               , const size_t&   colmax  = 1e6
00152               , const double&   value   = 0
00153               ) ;
00154 
00155   /// Destructor
00156   virtual ~AlgSmearing () {}
00157 
00158   /**
00159    * @brief Evaluates the matrix of weights distributed as 2-d Gaussian
00160    * 
00161    * If sigma=0 - matrix of weights is not used, but is filled out for print. 
00162    */
00163 
00164   void evaluateWeights();
00165 
00166   /// Prints the matrix of weights
00167   void printWeights();
00168 
00169   /// Prints memeber data
00170   void printInputPars();
00171 
00172   /**
00173    * @brief Get smearing weight
00174    * 
00175    * @param[in] dr - deviatin in rows from smeared pixel
00176    * @param[in] dc - deviatin in columns from smeared pixel
00177    */
00178   double weight(int dr, int dc) { return m_weights[abs(dr)][abs(dc)]; }
00179 
00180   /// Returns segment index in the ndarray
00181   const size_t& segind(){ return m_seg; }
00182 
00183   // Copy constructor and assignment are disabled by default
00184   AlgSmearing ( const AlgSmearing& ) ;
00185   AlgSmearing& operator = ( const AlgSmearing& ) ;
00186 
00187 
00188 protected:
00189 
00190 private:
00191 
00192   double   m_sigma;    // smearing sigma in pixel size
00193   int      m_nsm;      // number of pixels for smearing [i0-m_nsm, i0+m_nsm]
00194   int      m_nsm1;     // = m_nsm + 1
00195   double   m_thr_low;  // low threshold on pixel amplitude which will be involved in smearing
00196   unsigned m_opt;      // options for ndarray pre-fill
00197   unsigned m_pbits;    // pirnt control bit-word
00198   size_t   m_seg;      // segment index in the ndarray, <0 - for all segments
00199   size_t   m_rowmin;   // window for smearing
00200   size_t   m_rowmax;
00201   size_t   m_colmin;
00202   size_t   m_colmax;
00203   double   m_value;    // pre-fill and below threshold value
00204 
00205   ndarray<double,2> m_weights; //2-d array of weights
00206 
00207   /// Returns string name of the class for messanger
00208   std::string _name(){return std::string("ImgAlgos::AlgSmearing");}
00209 
00210 //--------------------
00211   /**
00212    * @brief Returns smeared intensity of a single-pixel
00213    * 
00214    * @param[in] nda_raw - ndarray with raw intensities
00215    * @param[in] r0 - row of the smeared pixel
00216    * @param[in] c0 - column of the smeared pixel
00217    */
00218 
00219 template <typename T>
00220 double _smearPixAmp(const ndarray<const T,2>& nda_raw, const size_t& r0, const size_t& c0)
00221 {
00222   const T *p_raw = nda_raw.data();
00223   size_t nrows = nda_raw.shape()[0];
00224   size_t ncols = nda_raw.shape()[1];
00225 
00226   double sum_aw = 0;
00227   double sum_w  = 0;
00228   double     w  = 0;
00229   unsigned ind  = 0;
00230 
00231   int rmin = std::max(0, int(r0-m_nsm));
00232   int rmax = std::min(nrows, r0+m_nsm+1);
00233   int cmin = std::max(0, int(c0-m_nsm));
00234   int cmax = std::min(ncols, c0+m_nsm+1);
00235 
00236   for (int r = rmin; r < rmax; r++) {
00237     for (int c = cmin; c < cmax; c++) {
00238 
00239       ind = r*ncols + c;
00240       w = weight(r-r0, c-c0);
00241       sum_w  += w;
00242       sum_aw += p_raw[ind] * w;
00243 
00244       //cout << "dr, dc, ind, w=" << r-r0 << " " << c-c0 << " " << ind << " " << w << endl;
00245     }
00246   }
00247   return (sum_w>0)? sum_aw / sum_w : m_value;
00248 }
00249 
00250 
00251 
00252 
00253 //--------------------
00254 
00255 public:
00256 
00257 //--------------------
00258   /**
00259    * @brief Smearing of the 2-d ndarray, one pass
00260    * 
00261    * @param[in]  nda_raw - ndarray with raw intensities
00262    * @param[out] nda_sme - ndarray with smeared intensities
00263    * 
00264    * If sigma=0 - smearing is turned off output array is a copy of input. 
00265    */
00266 
00267 template <typename T>
00268 void smearing(const ndarray<const T,2>& nda_raw, ndarray<T,2>& nda_sme)
00269 {
00270   const T* p_raw = nda_raw.data();
00271   T*       p_sme = nda_sme.data();
00272 
00273   if(m_sigma == 0) { std::memcpy(p_sme, p_raw, nda_raw.size()*sizeof(T)); return; }
00274 
00275   T      thr   = (T) m_thr_low;
00276   T      val   = (T) m_value;
00277   size_t nrows = nda_raw.shape()[0];
00278   size_t ncols = nda_raw.shape()[1];
00279 
00280   size_t rmin = std::max(0, int(m_rowmin));
00281   size_t rmax = std::min(nrows, m_rowmax+1);
00282   size_t cmin = std::max(0, int(m_colmin));
00283   size_t cmax = std::min(ncols, m_colmax+1);
00284 
00285   if(m_pbits & 128) MsgLog(_name(), info, "  seg:"   << m_seg
00286                                        << "  nrows:" << nrows
00287                                        << "  ncols:" << ncols
00288                                        << "  rmin:"  << rmin
00289                                        << "  rmax:"  << rmax
00290                                        << "  cmin:"  << cmin
00291                                        << "  cmax:"  << cmax
00292                                        << "  nda_raw.size:"  << nda_raw.size()
00293                                        << "  nda_sme.size:"  << nda_sme.size()
00294                            );
00295 
00296   if     (m_opt==0) std::fill_n(p_sme, int(nda_raw.size()), T(m_value));
00297   else if(m_opt==1) std::memcpy(p_sme, p_raw, nda_raw.size()*sizeof(T));
00298 
00299   for (size_t r = rmin; r < rmax; r++) {
00300     for (size_t c = cmin; c < cmax; c++) {
00301       unsigned ind = r*ncols + c;
00302       p_sme[ind] = (p_raw[ind]>thr) ? (T)_smearPixAmp<T>(nda_raw, r, c) : val;
00303     }
00304   }
00305 }
00306 
00307 //--------------------
00308 
00309 };
00310 
00311 } // namespace ImgAlgos
00312 
00313 #endif // IMGALGOS_ALGSMEARING_H

Generated on 19 Dec 2016 for PSDMSoftware by  doxygen 1.4.7