Main Page | Modules | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members

EMAN::MeanShrinkProcessor Class Reference

MeanShrinkProcessor shrinks an image by in an integer amount (and optionally by 1.5) taking the mean of the pixel neighbourhood. More...

#include <processor.h>

Inheritance diagram for EMAN::MeanShrinkProcessor:

Inheritance graph
[legend]
Collaboration diagram for EMAN::MeanShrinkProcessor:

Collaboration graph
[legend]
List of all members.

Public Member Functions

virtual EMDataprocess (const EMData *const image)
 The meanshrink processor has its own process function to minise memory usage - if this function was not over written the base Processor class would create copy of the input image and hand it to the process_inplace function.
virtual void process_inplace (EMData *image)
 Mean shrink inplace.
string get_desc () const
 Get the descrition of this specific processor.
virtual string get_name () const
 Get the processor's name.
virtual TypeDict get_param_types () const
 Get processor parameter information in a dictionary.

Static Public Member Functions

ProcessorNEW ()

Static Public Attributes

const string NAME = "math.meanshrink"

Private Member Functions

void accrue_mean (EMData *to, const EMData *const from, const int shrinkfactor)
 Accrue the local mean in the image 'from' to the image 'to' using the given shrinkfactor An internal function that encapsulates a routine common to both process and process inplace.
void accrue_mean_one_p_five (EMData *to, const EMData *const from)
 Accrue the local mean in the image 'from' to the image 'to' using the the special case shrink factor of 1.5 This is an internal function that encapsulates a routine common to both process and process inplace.

Detailed Description

MeanShrinkProcessor shrinks an image by in an integer amount (and optionally by 1.5) taking the mean of the pixel neighbourhood.

Author:
David Woolford (But is basically a copy of the old EMData::mean_shrink, probably written by Steven Ludtke )
Date:
May 2008
Parameters:
n The shrink factor

Definition at line 3227 of file processor.h.


Member Function Documentation

void MeanShrinkProcessor::accrue_mean EMData to,
const EMData *const   from,
const int  shrinkfactor
[private]
 

Accrue the local mean in the image 'from' to the image 'to' using the given shrinkfactor An internal function that encapsulates a routine common to both process and process inplace.

Parameters:
to the smaller image that will store the mean values
from the larger image that will be used to calculate the mean values
shrinkfactor the shrink amount

Definition at line 2152 of file processor.cpp.

References data, EMAN::EMData::get_const_data(), EMAN::EMData::get_data(), EMAN::EMData::get_xsize(), EMAN::EMData::get_ysize(), EMAN::EMData::get_zsize(), nx, ny, rdata, and EMAN::EMData::scale_pixel().

Referenced by process(), and process_inplace().

02153 {
02154         const float * const data = from->get_const_data();
02155         float* rdata = to->get_data();
02156 
02157         int nx = from->get_xsize();
02158         int ny = from->get_ysize();
02159         int nz = from->get_zsize();
02160         int nxy = nx*ny;
02161 
02162 
02163         int shrunken_nx = nx / shrink_factor;
02164         int shrunken_ny = ny / shrink_factor;
02165         int shrunken_nz = 1;
02166         int shrunken_nxy = shrunken_nx * shrunken_ny;
02167 
02168         int normalize_shrink_factor = shrink_factor * shrink_factor;
02169         int z_shrink_factor = 1;
02170 
02171         if (nz > 1) {
02172                 shrunken_nz = nz / shrink_factor;
02173                 normalize_shrink_factor *= shrink_factor;
02174                 z_shrink_factor = shrink_factor;
02175         }
02176 
02177         float invnormfactor = 1.0f/(float)normalize_shrink_factor;
02178 
02179         for (int k = 0; k < shrunken_nz; k++) {
02180                 int k_min = k * shrink_factor;
02181                 int k_max = k * shrink_factor + z_shrink_factor;
02182                 size_t cur_k = k * shrunken_nxy;
02183 
02184                 for (int j = 0; j < shrunken_ny; j++) {
02185                         int j_min = j * shrink_factor;
02186                         int j_max = j * shrink_factor + shrink_factor;
02187                         size_t cur_j = j * shrunken_nx + cur_k;
02188 
02189                         for (int i = 0; i < shrunken_nx; i++) {
02190                                 int i_min = i * shrink_factor;
02191                                 int i_max = i * shrink_factor + shrink_factor;
02192 
02193                                 float sum = 0;
02194                                 for (int kk = k_min; kk < k_max; kk++) {
02195                                         size_t cur_kk = kk * nxy;
02196 
02197                                         for (int jj = j_min; jj < j_max; jj++) {
02198                                                 size_t cur_jj = jj * nx + cur_kk;
02199                                                 for (int ii = i_min; ii < i_max; ii++) {
02200                                                         sum += data[ii + cur_jj];
02201                                                 }
02202                                         }
02203                                 }
02204                                 rdata[i + cur_j] = sum * invnormfactor;
02205                         }
02206                 }
02207         }
02208         to->scale_pixel((float)shrink_factor);
02209 }

void MeanShrinkProcessor::accrue_mean_one_p_five EMData to,
const EMData *const   from
[private]
 

Accrue the local mean in the image 'from' to the image 'to' using the the special case shrink factor of 1.5 This is an internal function that encapsulates a routine common to both process and process inplace.

Parameters:
to the smaller image that will store the mean values
from the larger image that will be used to calculate the mean values

Definition at line 2212 of file processor.cpp.

References data, EMAN::EMData::get_const_data(), EMAN::EMData::get_data(), EMAN::EMData::get_xsize(), EMAN::EMData::get_ysize(), nx, ny, EMAN::EMData::scale_pixel(), and EMAN::EMData::update().

Referenced by process(), and process_inplace().

02213 {
02214         int nx0 = from->get_xsize(), ny0 = from->get_ysize();   // the original size
02215 
02216         int nx = to->get_xsize(), ny = to->get_ysize();
02217 
02218         float *data = to->get_data();
02219         const float * const data0 = from->get_const_data();
02220 
02221         for (int j = 0; j < ny; j++) {
02222                 int jj = int(j * 1.5);
02223                 float jw0 = 1.0F, jw1 = 0.5F;   // 3x3 -> 2x2, so each new pixel should have 2.25 of the old pixels
02224                 if ( j%2 ) {
02225                         jw0 = 0.5F;
02226                         jw1 = 1.0F;
02227                 }
02228                 for (int i = 0; i < nx; i++) {
02229                         int ii = int(i * 1.5);
02230                         float iw0 = 1.0F, iw1 = 0.5F;
02231                         float w = 0.0F;
02232 
02233                         if ( i%2 ) {
02234                                 iw0 = 0.5F;
02235                                 iw1 = 1.0F;
02236                         }
02237                         if ( jj < ny0 ) {
02238                                 if ( ii < nx0 ) {
02239                                         data[j * nx + i] = data0[ jj * nx0 + ii ] * jw0 * iw0 ;
02240                                         w += jw0 * iw0 ;
02241                                         if ( ii+1 < nx0 ) {
02242                                                 data[j * nx + i] += data0[ jj * nx0 + ii + 1] * jw0 * iw1;
02243                                                 w += jw0 * iw1;
02244                                         }
02245                                 }
02246                                 if ( jj +1 < ny0 ) {
02247                                         if ( ii < nx0 ) {
02248                                                 data[j * nx + i] += data0[ (jj+1) * nx0 + ii ] * jw1 * iw0;
02249                                                 w += jw1 * iw0;
02250                                                 if ( ii+1 < nx0 ) {
02251                                                         data[j * nx + i] += data0[ (jj+1) * nx0 + ii + 1] * jw1 * iw1;
02252                                                         w += jw1 * iw1;
02253                                                 }
02254                                         }
02255                                 }
02256                         }
02257                         if ( w>0 ) data[j * nx + i] /= w;
02258                 }
02259         }
02260 
02261         to->update();
02262         to->scale_pixel((float)1.5);
02263 }

string EMAN::MeanShrinkProcessor::get_desc  )  const [inline, virtual]
 

Get the descrition of this specific processor.

This function must be overwritten by a subclass.

Returns:
The description of this processor.

Implements EMAN::Processor.

Definition at line 3250 of file processor.h.

03251                         {
03252                                 return "Shrink an image by a given amount , using the mean value found in the pixel neighborhood.";
03253                         }

virtual string EMAN::MeanShrinkProcessor::get_name  )  const [inline, virtual]
 

Get the processor's name.

Each processor is identified by a unique name.

Returns:
The processor's name.

Implements EMAN::Processor.

Definition at line 3255 of file processor.h.

03256                         {
03257                                 return NAME;
03258                         }

virtual TypeDict EMAN::MeanShrinkProcessor::get_param_types  )  const [inline, virtual]
 

Get processor parameter information in a dictionary.

Each parameter has one record in the dictionary. Each record contains its name, data-type, and description.

Returns:
A dictionary containing the parameter info.

Reimplemented from EMAN::Processor.

Definition at line 3264 of file processor.h.

References EMAN::TypeDict::put().

03265                         {
03266                                 TypeDict d;
03267                                 d.put("n", EMObject::FLOAT, "The shrink factor");
03268                                 return d;
03269                         }

Processor* EMAN::MeanShrinkProcessor::NEW  )  [inline, static]
 

Definition at line 3259 of file processor.h.

03260                         {
03261                                 return new MeanShrinkProcessor();
03262                         }

EMData * MeanShrinkProcessor::process const EMData *const   image  )  [virtual]
 

The meanshrink processor has its own process function to minise memory usage - if this function was not over written the base Processor class would create copy of the input image and hand it to the process_inplace function.

This latter approach mallocs and copies more memory than necessary

Parameters:
image the image that will be used to generate a 'mean shrunken' image
Exceptions:
ImageFormatException if the image is complex
ImageDimensionException if the image is 1D
InvalidValueException if the shrink amount is a nonzero integer, unless it is 1.5, which is an exceptional circumstance

Reimplemented from EMAN::Processor.

Definition at line 2047 of file processor.cpp.

References accrue_mean(), accrue_mean_one_p_five(), EMAN::EMData::copy_head(), EMAN::EMData::get_ndim(), EMAN::EMData::get_xsize(), EMAN::EMData::get_ysize(), EMAN::EMData::get_zsize(), ImageDimensionException, ImageFormatException, InvalidValueException, EMAN::EMData::is_complex(), nx, ny, EMAN::Dict::set_default(), EMAN::EMData::set_size(), and EMAN::EMData::update().

02048 {
02049         if (image->is_complex()) throw ImageFormatException("Error, the mean shrink processor does not work on complex images");
02050 
02051         if (image->get_ndim() == 1) { throw ImageDimensionException("Error, mean shrink works only for 2D & 3D images"); }
02052 
02053         float shrink_factor0 = params.set_default("n",0.0f);
02054         int shrink_factor = int(shrink_factor0);
02055         if (shrink_factor0 <= 1.0F || ((shrink_factor0 != shrink_factor) && (shrink_factor0 != 1.5F) ) ) {
02056                 throw InvalidValueException(shrink_factor0,
02057                                                                         "mean shrink: shrink factor must be >1 integer or 1.5");
02058         }
02059 
02060         int nx = image->get_xsize();
02061         int ny = image->get_ysize();
02062         int nz = image->get_zsize();
02063 
02064 
02065         // here handle the special averaging by 1.5 for 2D case
02066         if (shrink_factor0==1.5 ) {
02067                 if (nz > 1 ) throw InvalidValueException(shrink_factor0, "mean shrink: only support 2D images for shrink factor = 1.5");
02068 
02069                 int shrunken_nx = (int(nx / 1.5)+1)/2*2;        // make sure the output size is even
02070                 int shrunken_ny = (int(ny / 1.5)+1)/2*2;
02071                 EMData* result = new EMData(shrunken_nx,shrunken_ny,1);
02072 
02073                 accrue_mean_one_p_five(result,image);
02074                 result->update();
02075 
02076                 return result;
02077         }
02078 
02079         int shrunken_nx = nx / shrink_factor;
02080         int shrunken_ny = ny / shrink_factor;
02081         int shrunken_nz = 1;
02082 
02083         if (nz > 1) {
02084                 shrunken_nz = nz / shrink_factor;
02085         }
02086 
02087 //      EMData* result = new EMData(shrunken_nx,shrunken_ny,shrunken_nz);
02088         EMData* result = image->copy_head();
02089         result->set_size(shrunken_nx,shrunken_ny,shrunken_nz);
02090         accrue_mean(result,image,shrink_factor);
02091 
02092         result->update();
02093 
02094         return result;
02095 }

void MeanShrinkProcessor::process_inplace EMData image  )  [virtual]
 

Mean shrink inplace.

Parameters:
image the image that will be 'mean shrunken' inplace
Exceptions:
ImageFormatException if the image is complex
ImageDimensionException if the image is 1D
InvalidValueException if the shrink amount is a nonzero integer, unless it is 1.5, which is an exceptional circumstance

Implements EMAN::Processor.

Definition at line 2097 of file processor.cpp.

References accrue_mean(), accrue_mean_one_p_five(), EMAN::EMData::copy(), EMAN::EMData::get_ndim(), EMAN::EMData::get_xsize(), EMAN::EMData::get_ysize(), EMAN::EMData::get_zsize(), ImageDimensionException, ImageFormatException, InvalidValueException, EMAN::EMData::is_complex(), nx, ny, EMAN::Dict::set_default(), EMAN::EMData::set_size(), EMAN::EMData::to_zero(), and EMAN::EMData::update().

02098 {
02099         if (image->is_complex()) throw ImageFormatException("Error, the mean shrink processor does not work on complex images");
02100 
02101         if (image->get_ndim() == 1) { throw ImageDimensionException("Error, mean shrink works only for 2D & 3D images"); }
02102 
02103         float shrink_factor0 = params.set_default("n",0.0f);
02104         int shrink_factor = int(shrink_factor0);
02105         if (shrink_factor0 <= 1.0F || ((shrink_factor0 != shrink_factor) && (shrink_factor0 != 1.5F) ) ) {
02106                 throw InvalidValueException(shrink_factor0,
02107                                                                         "mean shrink: shrink factor must be >1 integer or 1.5");
02108         }
02109 
02110 /*      if ((nx % shrink_factor != 0) || (ny % shrink_factor != 0) ||
02111         (nz > 1 && (nz % shrink_factor != 0))) {
02112         throw InvalidValueException(shrink_factor,
02113         "Image size not divisible by shrink factor");
02114 }*/
02115 
02116         int nx = image->get_xsize();
02117         int ny = image->get_ysize();
02118         int nz = image->get_zsize();
02119         // here handle the special averaging by 1.5 for 2D case
02120         if (shrink_factor0==1.5 ) {
02121                 if (nz > 1 ) throw InvalidValueException(shrink_factor0, "mean shrink: only support 2D images for shrink factor = 1.5");
02122 
02123                 int shrunken_nx = (int(nx / 1.5)+1)/2*2;        // make sure the output size is even
02124                 int shrunken_ny = (int(ny / 1.5)+1)/2*2;
02125 
02126                 EMData* orig = image->copy();
02127                 image->set_size(shrunken_nx, shrunken_ny, 1);   // now nx = shrunken_nx, ny = shrunken_ny
02128                 image->to_zero();
02129 
02130                 accrue_mean_one_p_five(image,orig);
02131 
02132                 if( orig ) {
02133                         delete orig;
02134                         orig = 0;
02135                 }
02136                 image->update();
02137 
02138                 return;
02139         }
02140 
02141         accrue_mean(image,image,shrink_factor);
02142 
02143         int shrunken_nx = nx / shrink_factor;
02144         int shrunken_ny = ny / shrink_factor;
02145         int shrunken_nz = 1;
02146         if (nz > 1) shrunken_nz = nz / shrink_factor;
02147 
02148         image->update();
02149         image->set_size(shrunken_nx, shrunken_ny, shrunken_nz);
02150 }


Member Data Documentation

const string MeanShrinkProcessor::NAME = "math.meanshrink" [static]
 

Definition at line 120 of file processor.cpp.


The documentation for this class was generated from the following files:
Generated on Thu Dec 9 13:47:58 2010 for EMAN2 by  doxygen 1.3.9.1