cmtkScalarImageSimilarityRMI.cxx

Go to the documentation of this file.
00001 /*
00002 //
00003 //  Copyright 1997-2009 Torsten Rohlfing
00004 //
00005 //  Copyright 2004-2010 SRI International
00006 //
00007 //  This file is part of the Computational Morphometry Toolkit.
00008 //
00009 //  http://www.nitrc.org/projects/cmtk/
00010 //
00011 //  The Computational Morphometry Toolkit is free software: you can
00012 //  redistribute it and/or modify it under the terms of the GNU General Public
00013 //  License as published by the Free Software Foundation, either version 3 of
00014 //  the License, or (at your option) any later version.
00015 //
00016 //  The Computational Morphometry Toolkit is distributed in the hope that it
00017 //  will be useful, but WITHOUT ANY WARRANTY; without even the implied
00018 //  warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00019 //  GNU General Public License for more details.
00020 //
00021 //  You should have received a copy of the GNU General Public License along
00022 //  with the Computational Morphometry Toolkit.  If not, see
00023 //  <http://www.gnu.org/licenses/>.
00024 //
00025 //  $Revision: 2398 $
00026 //
00027 //  $LastChangedDate: 2010-10-05 14:54:37 -0700 (Tue, 05 Oct 2010) $
00028 //
00029 //  $LastChangedBy: torstenrohlfing $
00030 //
00031 */
00032 
00033 #include "cmtkScalarImageSimilarity.h"
00034 
00035 #include <Base/cmtkMathUtil.h>
00036 
00037 namespace
00038 cmtk
00039 {
00040 
00043 
00044 
00045 ScalarImageSimilarity::ReturnType
00046 ScalarImageSimilarity::GetRegionalMutualInformation
00047 ( const ScalarImage* image0, const ScalarImage* image1, const int radius )
00048 {
00049   // printf("REGIONAL MUTUAL INFORMATION\n");
00050   const ScalarImage::IndexType& dims = image0->GetDims();
00051   int nrows = dims[1];
00052   int ncols = dims[0];
00053   
00054   int d = 2*radius+1;
00055   int N = (ncols-2*radius)*(nrows-2*radius);
00056   int d2 = d*d;
00057   int dim = 2*d2;
00058   
00059   Types::DataItem* pts = Memory::AllocateArray<Types::DataItem>( N*dim );
00060   
00061   
00062   Types::DataItem tmp1, tmp2;
00063   
00064   const TypedArray *data1 = image0->GetPixelData();
00065   const TypedArray *data2 = image1->GetPixelData();
00066   
00067   
00068   int idx,nidx,lidx;
00069   nidx = 0; idx = 0; lidx = 0;
00070   
00071 // printf("creating neighborhood...\n");
00072 // CREATE NEIGHBORHOOD VECTORS
00073   for (int i=radius; i<nrows-radius; i++) 
00074     {
00075     for (int j=radius; j<ncols-radius; j++) 
00076       {
00077       lidx = 0;
00078       for (int ii=-radius; ii<=radius; ii++) 
00079         {
00080         for (int jj=-radius; jj<=radius; jj++) 
00081           {
00082           idx = (i+ii)*ncols + j+jj;
00083           
00084           data1->Get(tmp1,idx);
00085           data2->Get(tmp2,idx);
00086           pts[lidx*N + nidx] = tmp1;
00087           pts[(lidx+d2)*N + nidx] = tmp2;
00088           lidx++;
00089           }
00090         }
00091       nidx++;
00092       }
00093     }
00094 // printf("done.\n");
00095   
00096   
00097 // SUBTRACT MEAN
00098 // printf("subtracting mean...\n");
00099   std::vector<double> mean(dim,0.0);
00100   
00101   for (int i=0; i<dim; i++) 
00102     {
00103     for (int j=0; j<N; j++) 
00104       {
00105       mean[i] += pts[i*N+j];
00106       }
00107     }
00108   for (int i=0; i<dim; i++) 
00109     {
00110     mean[i] /= N;
00111     }
00112   
00113   for (int i=0; i<dim; i++) 
00114     {
00115     for (int j=0; j<N; j++) 
00116       {
00117       pts[i*N+j] -= mean[i];
00118       }
00119     }
00120 // printf("done.\n");
00121   
00122         
00123 
00124 // CALCULATE JOINT COVARIANCE
00125 // printf("calculating joint covariance...\n");
00126   Matrix2D<Types::DataItem> cM( dim, dim );
00127  
00128   ScalarImageSimilarity::ReturnType sum;
00129   int iN, jN;
00130   
00131   for (int i=0; i<dim; i++) 
00132     {
00133     for (int j=i; j<dim; j++) 
00134       {
00135       sum = 0.0;
00136       iN = i*N;
00137       jN = j*N;
00138       
00139       for (int k=0; k<N; k++) 
00140         {
00141         sum += pts[iN+k]*pts[jN+k];
00142         }
00143       cM[i][j] = sum/N;
00144       cM[j][i] = cM[i][j];
00145       // printf("cM[%d][%d] = %f\n", i,j,cM[i][j]);
00146       }
00147     }
00148   double dt3 = MathUtil::CholeskyDeterminant(cM, dim);
00149 // printf("done.\n");
00150   
00151   
00152   
00153 // CALCULATE MARGINAL COVARIANCES
00154 // printf("calculating marginal covariances...\n");
00155   Matrix2D<Types::DataItem> mcM( dim/2, dim/2 );
00156  
00157   // image0's bloc
00158   for (int i=0; i<dim/2; i++) 
00159     {
00160     for (int j=0; j<dim/2; j++) 
00161       {
00162       mcM[i][j] = cM[i][j];
00163       }
00164     }
00165   double dt1 = MathUtil::CholeskyDeterminant(mcM, dim/2);
00166   
00167   // image1's bloc
00168   for (int i=0; i<dim/2; i++) 
00169     {
00170     for (int j=0; j<dim/2; j++) 
00171       {
00172       mcM[i][j] = cM[i+dim/2][j+dim/2];
00173       }
00174     }
00175   double dt2 =  MathUtil::CholeskyDeterminant(mcM, dim/2);
00176   
00177   double alpha = 1.41893853320467;
00178     
00179   double v1 = dim/2*alpha + .5*log(dt1);
00180   double v2 = dim/2*alpha + .5*log(dt2);
00181   double v3 = dim*alpha   + .5*log(dt3);
00182     
00183   // printf("v1=%f, v2=%f, v3=%f\n",v1,v2,v3);
00184     
00185   return ((ScalarImageSimilarity::ReturnType) (v1+v2-v3));
00186 }
00187 
00188 } // namespace cmtk
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines