96 cout <<
"The Median Root Prior (MRP) is implemented for several types of neighborhood. The parameters are described below, and a" << endl;
97 cout <<
"template configuration file for parameters selection can be found in the configuration folder (config/optimizer/MRP.conf)." << endl;
98 cout <<
"The configuration of this penalty can only be done through a configuration file. It is not possible to parameterize it" << endl;
99 cout <<
"directly from the command line. The current implementation is the simplest one, based on the following reference:" << endl;
100 cout <<
"S. Alenius and U Ruotsalainen, \"Bayesian image reconstruction for emission tomography based on the median root prior\"," << endl;
101 cout <<
"European Journal of Nuclear Medicine, vol. 24, pp. 258-265, 1997." << endl;
102 cout <<
"------------" << endl;
103 cout <<
"Neighborhood" << endl;
104 cout <<
"------------" << endl;
105 cout <<
"The neighborhood is set by the 'neighborhood shape' keyword and can be described using one of the following setting:" << endl;
106 cout <<
"[6-nearest]: Consider the 6 nearest neighbors, i.e. 2 along each dimension. In 2D, only 4 in the plane are used." << endl;
107 cout <<
"[box]: Consider all voxels included in a box centered on the voxel of interest. The size of the box is parameterized" << endl;
108 cout <<
" using the 'box neighborhood order' keyword. The side of the box is equal to '2*order+1'. The 8 corner voxels" << endl;
109 cout <<
" can also be excluded from the neighborhood by setting the 'exclude box neighborhood corners' keyword to 1." << endl;
110 cout <<
"[sphere]: Consider all voxels whose center is included in a sphere centered on the voxel of interest and of radius" << endl;
111 cout <<
" provided by the 'sphere neighborhood radius (mm)' keyword." << endl;
122 string key_word =
"";
127 key_word =
"neighborhood shape";
130 Cerr(
"***** iPenaltyMedianRootPrior::ReadConfigurationFile() -> Failed to get the '" << key_word <<
"' keyword !" << endl);
134 if (buffer ==
"sphere")
138 key_word =
"sphere neighborhood radius (mm)";
141 Cerr(
"***** iPenaltyMedianRootPrior::ReadConfigurationFile() -> Failed to get the '" << key_word <<
"' keyword !" << endl);
146 else if (buffer ==
"box")
150 key_word =
"box neighborhood order";
153 Cerr(
"***** iPenaltyMedianRootPrior::ReadConfigurationFile() -> Failed to get the '" << key_word <<
"' keyword !" << endl);
157 key_word =
"exclude box neighborhood corners";
160 Cerr(
"***** iPenaltyMedianRootPrior::ReadConfigurationFile() -> Failed to get the '" << key_word <<
"' keyword !" << endl);
165 else if (buffer ==
"6-nearest")
172 Cerr(
"***** iPenaltyMedianRootPrior::ReadConfigurationFile() -> Unknown neighborhood type '" << buffer <<
"' !" << endl);
188 Cerr(
"***** iPenaltyMedianRootPrior::ReadOptionsList() -> Options can be specified only using a configuration file !" << endl);
202 Cerr(
"***** iPenaltyMarkovRandomField::CheckSpecificParameters() -> Should provide a neighborhood type !" << endl);
208 Cerr(
"***** iPenaltyMarkovRandomField::CheckSpecificParameters() -> Provided radius of the sphere neighborhood (" <<
m_neighborhoodSphereRadius <<
") is negative" << endl);
213 Cerr(
"***** iPenaltyMarkovRandomField::CheckSpecificParameters() -> Provided order of the box neighborhood (" <<
m_neighborhoodBoxOrder <<
") is negative" << endl);
230 Cerr(
"***** iPenaltyMedianRootPrior::InitializeSpecific() -> Failed to build the neighborhood !" << endl);
245 Cout(
"iPenaltyMedianRootPrior::InitializeSpecific() -> Use the Median Root Prior" << endl);
251 Cout(
" --> shape of neighborhood: sphere" << endl);
256 Cout(
" --> shape of neighborhood: box" << endl);
262 Cout(
" --> shape of neighborhood: 6-nearest" << endl);
282 Cerr(
"***** iPenaltyMedianRootPrior::BuildNeighborhoodKernel() -> Neighborhood kernel has already been created !" << endl);
311 INTNB nb_voxels_in_neighborhood = 0;
313 for (
INTNB vox_z = -radius_vox_z; vox_z<=radius_vox_z; vox_z++)
314 for (
INTNB vox_y = -radius_vox_y; vox_y<=radius_vox_y; vox_y++)
315 for (
INTNB vox_x = -radius_vox_x; vox_x<=radius_vox_x; vox_x++)
318 FLTNB squareDistance = ((
FLTNB)(vox_x*vox_x))*vox_size_x*vox_size_x
319 + ((
FLTNB)(vox_y*vox_y))*vox_size_y*vox_size_y
320 + ((
FLTNB)(vox_z*vox_z))*vox_size_z*vox_size_z;
327 nb_voxels_in_neighborhood++;
331 m_neighborhoodMaxNbVoxels = nb_voxels_in_neighborhood;
348 INTNB nb_voxels_in_neighborhood = 0;
350 for (
INTNB vox_z = -neighborhood_box_order_z; vox_z<=neighborhood_box_order_z; vox_z++)
362 nb_voxels_in_neighborhood++;
366 m_neighborhoodMaxNbVoxels = nb_voxels_in_neighborhood;
398 Cerr(
"***** iPenaltyMedianRootPrior::BuildNeighborhoodKernel() -> The provided shape of neighborhood (" <<
m_neighborhoodShape <<
") is unknown !" << endl);
418 INTNB index_x = a_voxel % nb_vox_x;
419 INTNB index_y = (a_voxel/nb_vox_x) % nb_vox_y;
420 INTNB index_z = a_voxel / nb_vox_xy;
431 if ( neighbor_x>=0 && neighbor_x<nb_vox_x && neighbor_y>=0 && neighbor_y<nb_vox_y && neighbor_z>=0 && neighbor_z<nb_vox_z )
458 Cerr(
"***** iPenaltyMedianRootPrior::LocalPreProcessingStep() -> A problem occurred while building specific neighborhood of voxel " << a_voxel <<
" !" << endl);
464 Cerr(
"***** iPenaltyMedianRootPrior::LocalPreProcessingStep() -> A problem occurred while computing the median in neighborhood of voxel " << a_voxel <<
" !" << endl);
480 [a_voxel,a_tbf,a_rbf,a_cbf,a_th,
this](
INTNB i1,
INTNB i2)
483 if (i1 == -1)
return false;
484 if (i2 == -1)
return true;
530 FLTNB first_derivative = 0.;
533 return first_derivative;
545 FLTNB second_derivative = 0.;
548 return second_derivative;
int m_penaltyDerivativesOrder
oImageSpace * mp_ImageSpace
FLTNB GetVoxSizeX()
Get the voxel's size along the X axis, in mm.
FLTNB GetVoxSizeZ()
Get the voxel's size along the Z axis, in mm.
#define MRF_NEIGHBORHOOD_SPHERE
FLTNB GetVoxSizeY()
Get the voxel's size along the Y axis, in mm.
oImageDimensionsAndQuantification * mp_ImageDimensionsAndQuantification
int ReadDataASCIIFile(const string &a_file, const string &a_keyword, T *ap_return, int a_nbElts, bool a_mandatoryFlag)
Look for "a_nbElts" elts in the "a_file" file matching the "a_keyword" string passed as parameter a...
INTNB GetNbVoxXY()
Get the number of voxels in a slice.
This class is designed to generically described any penalty applied to MAP algorithms.
#define KEYWORD_MANDATORY
int GetNbThreadsForImageComputation()
Get the number of threads used for image operations.
#define MRF_NEIGHBORHOOD_BOX
INTNB GetNbVoxX()
Get the number of voxels along the X axis.
INTNB GetNbVoxZ()
Get the number of voxels along the Z axis.
#define MRF_NEIGHBORHOOD_6_NEAREST
INTNB GetNbVoxY()
Get the number of voxels along the Y axis.
#define KEYWORD_OPTIONAL_ERROR