From 99afedee7b3cd032bf2b42a30c15b70f39097b34 Mon Sep 17 00:00:00 2001 From: Jordi Inglada <jordi.inglada@cesbio.cnes.fr> Date: Tue, 8 Jun 2010 15:41:18 +0200 Subject: [PATCH] BUG: OverallAccuracy is null --- Code/Learning/otbConfusionMatrixCalculator.h | 8 ++-- .../Learning/otbConfusionMatrixCalculator.txx | 44 +++++++++++++++++++ .../otbConfusionMatrixCalculatorTest.cxx | 24 +++++++++- 3 files changed, 71 insertions(+), 5 deletions(-) diff --git a/Code/Learning/otbConfusionMatrixCalculator.h b/Code/Learning/otbConfusionMatrixCalculator.h index 76108653d1..87a93726b0 100644 --- a/Code/Learning/otbConfusionMatrixCalculator.h +++ b/Code/Learning/otbConfusionMatrixCalculator.h @@ -67,9 +67,10 @@ public: itkGetConstObjectMacro(ReferenceLabels, RefListLabelType); itkSetObjectMacro(ProducedLabels, ProdListLabelType); itkGetConstObjectMacro(ProducedLabels, ProdListLabelType); - itkGetConstMacro(KappaIndex, double); - itkGetConstMacro(OverallAccuracy, double); - itkGetConstMacro(NumberOfClasses, unsigned short); + itkGetMacro(KappaIndex, double); + itkGetMacro(OverallAccuracy, double); + itkGetMacro(NumberOfClasses, unsigned short); + itkGetMacro(NumberOfSamples, unsigned long); itkGetMacro(ConfusionMatrix, ConfusionMatrixType); protected: @@ -90,6 +91,7 @@ private: std::map<int,int> m_MapOfClasses; unsigned short m_NumberOfClasses; + unsigned long m_NumberOfSamples; ConfusionMatrixType m_ConfusionMatrix; diff --git a/Code/Learning/otbConfusionMatrixCalculator.txx b/Code/Learning/otbConfusionMatrixCalculator.txx index 0f8cb8d219..a5e9eaf127 100644 --- a/Code/Learning/otbConfusionMatrixCalculator.txx +++ b/Code/Learning/otbConfusionMatrixCalculator.txx @@ -64,6 +64,8 @@ ConfusionMatrixCalculator<TRefListLabel,TProdListLabel> throw itk::ExceptionObject(__FILE__, __LINE__, "ListSample size missmatch", ITK_LOCATION); } + m_NumberOfSamples = m_ReferenceLabels->Size(); + // count de number of classes int countClasses = 0; @@ -82,6 +84,11 @@ ConfusionMatrixCalculator<TRefListLabel,TProdListLabel> m_NumberOfClasses = countClasses; + std::vector< long int > samplesPerClass; + + for(unsigned int i=0; i<m_NumberOfClasses; i++) + samplesPerClass.push_back(0); + m_ConfusionMatrix = ConfusionMatrixType(m_NumberOfClasses, m_NumberOfClasses); m_ConfusionMatrix.Fill(0); @@ -96,12 +103,49 @@ ConfusionMatrixCalculator<TRefListLabel,TProdListLabel> int refPos = m_MapOfClasses[refLabel]; int prodPos = m_MapOfClasses[prodLabel]; + ++samplesPerClass[refPos]; m_ConfusionMatrix( refPos,prodPos )+=1; ++refIterator; ++prodIterator; } + + + otbGenericMsgDebugMacro(<<"Confusion matrix " << m_ConfusionMatrix); + + for(unsigned int i=0; i<m_NumberOfClasses; i++) + otbGenericMsgDebugMacro(<<"Samples per class " << samplesPerClass[i]); + + this->m_OverallAccuracy = 0.; + for (unsigned int i = 0;i<m_NumberOfClasses;++i) + { + this->m_OverallAccuracy += m_ConfusionMatrix(i,i); + } + + this->m_OverallAccuracy/=static_cast<double>(m_NumberOfSamples); + + otbGenericMsgDebugMacro(<<"OA " << this->m_OverallAccuracy); + + + double luckyRate = 0.; + for (unsigned int i = 0;i<m_NumberOfClasses;++i) + { + double sum_ij = 0.; + double sum_ji = 0.; + for (unsigned int j = 0;j<m_NumberOfClasses;++j) + { + sum_ij +=m_ConfusionMatrix(i,j); + sum_ji +=m_ConfusionMatrix(j,i); + } + luckyRate+=sum_ij*sum_ji; + } + + + luckyRate/=vcl_pow(m_NumberOfSamples,2.0); + + double m_KappaIndex = (m_OverallAccuracy-luckyRate)/(1-luckyRate); + } diff --git a/Testing/Code/Learning/otbConfusionMatrixCalculatorTest.cxx b/Testing/Code/Learning/otbConfusionMatrixCalculatorTest.cxx index b61df7d81c..e5c16ad8a0 100644 --- a/Testing/Code/Learning/otbConfusionMatrixCalculatorTest.cxx +++ b/Testing/Code/Learning/otbConfusionMatrixCalculatorTest.cxx @@ -177,6 +177,11 @@ int otbConfusionMatrixCalculatorUpdate(int argc, char* argv[]) std::cerr << "Wrong number of classes" << std::endl; return EXIT_FAILURE; } + if( calculator->GetNumberOfSamples() != nbSamples ) + { + std::cerr << "Wrong number of samples" << std::endl; + return EXIT_FAILURE; + } CalculatorType::ConfusionMatrixType confmat = calculator->GetConfusionMatrix(); @@ -186,8 +191,11 @@ int otbConfusionMatrixCalculatorUpdate(int argc, char* argv[]) for (int j = 0; j < nbClasses; j++) { double goodValue = 0.0; - if (i == j) goodValue = nbSamples / nbClasses; - if (confmat(i, j) != goodValue) totalError += confmat(i, j); + if (i == j) + goodValue = nbSamples / nbClasses; + else + if (confmat(i, j) != goodValue) + totalError += confmat(i, j); } if( totalError > 0.001 ) @@ -197,6 +205,18 @@ int otbConfusionMatrixCalculatorUpdate(int argc, char* argv[]) return EXIT_FAILURE; } + if( calculator->GetOverallAccuracy() != 1.0 ) + { + std::cerr<< "OA = " << calculator->GetOverallAccuracy() << std::endl; + return EXIT_FAILURE; + } + + if( calculator->GetKappaIndex() != 1.0 ) + { + std::cerr<< "OA = " << calculator->GetKappaIndex() << std::endl; + return EXIT_FAILURE; + } + return EXIT_SUCCESS; } -- GitLab