From d39df137f19ee2fc605e0b2ada43d19a82511124 Mon Sep 17 00:00:00 2001 From: Ludovic Hussonnois <ludovic.hussonnois@c-s.fr> Date: Fri, 14 Apr 2017 15:43:30 +0100 Subject: [PATCH] REFAC: Inherit ContingencyTable from itk::Object --- .../app/otbComputeConfusionMatrix.cxx | 11 ++-- .../app/otbTrainVectorClassifier.cxx | 15 +++-- .../include/otbContingencyTable.h | 65 ++++++++++++++----- .../include/otbContingencyTableCalculator.h | 5 +- .../include/otbContingencyTableCalculator.txx | 7 +- .../otbContingencyTableCalculatorTest.cxx | 11 ++-- 6 files changed, 75 insertions(+), 39 deletions(-) diff --git a/Modules/Applications/AppClassification/app/otbComputeConfusionMatrix.cxx b/Modules/Applications/AppClassification/app/otbComputeConfusionMatrix.cxx index de72549233..bfc3098307 100644 --- a/Modules/Applications/AppClassification/app/otbComputeConfusionMatrix.cxx +++ b/Modules/Applications/AppClassification/app/otbComputeConfusionMatrix.cxx @@ -80,6 +80,7 @@ public: typedef ConfusionMatrixMeasurementsType::MeasurementType MeasurementType; typedef ContingencyTable<ClassLabelType> ContingencyTableType; + typedef ContingencyTableType::Pointer ContingencyTablePointerType; private: @@ -207,16 +208,16 @@ private: } } - void LogContingencyTable(const ContingencyTableType& contingencyTable) + void LogContingencyTable(const ContingencyTablePointerType& contingencyTable) { - otbAppLogINFO("Contingency table: reference labels (rows) vs. produced labels (cols)\n" << contingencyTable); + otbAppLogINFO("Contingency table: reference labels (rows) vs. produced labels (cols)\n" << (*contingencyTable.GetPointer())); } - void m_WriteContingencyTable(const ContingencyTableType& contingencyTable) + void m_WriteContingencyTable(const ContingencyTablePointerType& contingencyTable) { std::ofstream outFile; outFile.open( this->GetParameterString( "out" ).c_str() ); - outFile << contingencyTable.to_csv(); + outFile << contingencyTable->to_csv(); outFile.close(); } @@ -397,7 +398,7 @@ private: calculator->Compute( itRef, itInput,sid.refhasnodata,sid.refnodata,sid.prodhasnodata,sid.prodnodata); } - ContingencyTableType contingencyTable = calculator->BuildContingencyTable(); + ContingencyTablePointerType contingencyTable = calculator->BuildContingencyTable(); LogContingencyTable(contingencyTable); m_WriteContingencyTable(contingencyTable); } diff --git a/Modules/Applications/AppClassification/app/otbTrainVectorClassifier.cxx b/Modules/Applications/AppClassification/app/otbTrainVectorClassifier.cxx index 52952b22f4..db1226b04e 100644 --- a/Modules/Applications/AppClassification/app/otbTrainVectorClassifier.cxx +++ b/Modules/Applications/AppClassification/app/otbTrainVectorClassifier.cxx @@ -49,6 +49,9 @@ public: typedef ConfusionMatrixCalculatorType::ConfusionMatrixType ConfusionMatrixType; typedef ConfusionMatrixCalculatorType::MapOfIndicesType MapOfIndicesType; typedef ConfusionMatrixCalculatorType::ClassLabelType ClassLabelType; + + typedef ContingencyTable<ClassLabelType> ContingencyTableType; + typedef ContingencyTableType::Pointer ContingencyTablePointerType; protected: void DoInit() @@ -80,14 +83,14 @@ protected: } else { - ContingencyTable<ClassLabelType> table = ComputeContingencyTable( m_PredictedList, - m_ClassificationSamplesWithLabel.labeledListSample ); + ContingencyTablePointerType table = ComputeContingencyTable( m_PredictedList, + m_ClassificationSamplesWithLabel.labeledListSample ); WriteContingencyTable( table ); } } - ContingencyTable<ClassLabelType> ComputeContingencyTable(const TargetListSampleType::Pointer &predictedListSample, - const TargetListSampleType::Pointer &performanceLabeledListSample) + ContingencyTablePointerType ComputeContingencyTable(const TargetListSampleType::Pointer &predictedListSample, + const TargetListSampleType::Pointer &performanceLabeledListSample) { typedef ContingencyTableCalculator<ClassLabelType> ContigencyTableCalcutaltorType; @@ -103,14 +106,14 @@ protected: } - void WriteContingencyTable(const ContingencyTable<ClassLabelType> & table) + void WriteContingencyTable(const ContingencyTablePointerType& table) { if(IsParameterEnabled("io.confmatout")) { // Write contingency table std::ofstream outFile; outFile.open( this->GetParameterString( "io.confmatout" ).c_str() ); - outFile << table.to_csv(); + outFile << table->to_csv(); } } diff --git a/Modules/Learning/Unsupervised/include/otbContingencyTable.h b/Modules/Learning/Unsupervised/include/otbContingencyTable.h index d1996e66a3..04d515d6d0 100644 --- a/Modules/Learning/Unsupervised/include/otbContingencyTable.h +++ b/Modules/Learning/Unsupervised/include/otbContingencyTable.h @@ -24,24 +24,39 @@ #include <vector> #include <iostream> #include <iomanip> +#include <itkObject.h> +#include <itkObjectFactory.h> #include <itkVariableSizeMatrix.h> namespace otb { template<class TClassLabel> -class ContingencyTable +class ContingencyTable : public itk::Object { public: + /** Standard class typedefs */ + typedef ContingencyTable Self; + typedef itk::Object Superclass; + typedef itk::SmartPointer<Self> Pointer; + typedef itk::SmartPointer<const Self> ConstPointer; + + /** Run-time type information (and related methods). */ + itkTypeMacro(ContingencyTableCalculator, itk::Object); + + /** Method for creation through the object factory. */ + itkNewMacro(Self); + typedef itk::VariableSizeMatrix<unsigned long> MatrixType; - typedef std::vector<TClassLabel> LabelList; + typedef std::vector<TClassLabel> LabelList; MatrixType matrix; - ContingencyTable(LabelList referenceLabels, LabelList producedLabels) : refLabels( referenceLabels ), - prodLabels( producedLabels ) + void SetLabels(LabelList referenceLabels, LabelList producedLabels) { - unsigned int rows = static_cast<unsigned int>(refLabels.size()); - unsigned int cols = static_cast<unsigned int>(prodLabels.size()); + m_RefLabels = referenceLabels; + m_ProdLabels = producedLabels; + unsigned int rows = static_cast<unsigned int>(m_RefLabels.size()); + unsigned int cols = static_cast<unsigned int>(m_ProdLabels.size()); matrix.SetSize( rows, cols ); matrix.Fill( 0 ); } @@ -51,19 +66,19 @@ public: // Retrieve the maximal width from the matrix and the labels size_t maxWidth = 6; - for( size_t i = 0; i << contingencyTable.prodLabels.size(); ++i ) + for( size_t i = 0; i << contingencyTable.m_ProdLabels.size(); ++i ) { std::ostringstream oss; - oss << contingencyTable.prodLabels[i]; + oss << contingencyTable.m_ProdLabels[i]; size_t length = oss.str().length(); if( length > maxWidth ) maxWidth = length; } - for( size_t i = 0; i << contingencyTable.refLabels.size(); ++i ) + for( size_t i = 0; i << contingencyTable.m_RefLabels.size(); ++i ) { std::ostringstream oss; - oss << contingencyTable.refLabels[i]; + oss << contingencyTable.m_RefLabels[i]; size_t length = oss.str().length(); if( length > maxWidth ) maxWidth = length; @@ -85,16 +100,16 @@ public: // Write the first line of the matrix (produced labels) o << std::setfill(' ') << std::setw( width ) << "labels"; - for( size_t i = 0; i < contingencyTable.prodLabels.size(); ++i ) + for( size_t i = 0; i < contingencyTable.m_ProdLabels.size(); ++i ) { - o << std::setfill(' ') << std::setw( width ) << contingencyTable.prodLabels[i]; + o << std::setfill(' ') << std::setw( width ) << contingencyTable.m_ProdLabels[i]; } o << std::endl; // For each line write the reference label, then the count value for( unsigned int i = 0; i < contingencyTable.matrix.Rows(); ++i ) { - o << std::setfill(' ') << std::setw( width ) << contingencyTable.refLabels[i]; + o << std::setfill(' ') << std::setw( width ) << contingencyTable.m_RefLabels[i]; for( unsigned int j = 0; j < contingencyTable.matrix.Cols(); ++j ) { o << std::setfill(' ') << std::setw( width ) << contingencyTable.matrix( i, j ); @@ -111,16 +126,16 @@ public: std::ostringstream oss; oss << "labels"; - for( size_t i = 0; i < prodLabels.size(); ++i ) + for( size_t i = 0; i < m_ProdLabels.size(); ++i ) { - oss << separator << prodLabels[i]; + oss << separator << m_ProdLabels[i]; } oss << std::endl; // For each line write the reference label, then the count value for( unsigned int i = 0; i < matrix.Rows(); ++i ) { - oss << refLabels[i]; + oss << m_RefLabels[i]; for( unsigned int j = 0; j < matrix.Cols(); ++j ) { oss << separator << matrix( i, j ); @@ -132,9 +147,23 @@ public: return oss.str(); } +protected: + ContingencyTable() + { + SetLabels(LabelList{}, LabelList{}); + } + ~ContingencyTable() ITK_OVERRIDE {} + void PrintSelf(std::ostream& os, itk::Indent itkNotUsed(indent)) const ITK_OVERRIDE + { + os << *this; + } + private: - LabelList refLabels; - LabelList prodLabels; + ContingencyTable(const Self &); //purposely not implemented + void operator=(const Self &); //purposely not implemented + + LabelList m_RefLabels; + LabelList m_ProdLabels; }; diff --git a/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.h b/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.h index 7f06bf7d18..ae30bf8441 100644 --- a/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.h +++ b/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.h @@ -53,7 +53,8 @@ public: /** Method for creation through the object factory. */ itkNewMacro(Self); - typedef ContingencyTable<TClassLabel> ContingencyTableType; + typedef ContingencyTable<TClassLabel> ContingencyTableType; + typedef typename ContingencyTableType::Pointer ContingencyTablePointerType; typedef typename std::map<TClassLabel, unsigned long> CountMapType; typedef typename std::map<TClassLabel, CountMapType > MapOfClassesType; @@ -72,7 +73,7 @@ public: itkGetConstMacro(NumberOfSamples, unsigned long); void Clear(); - ContingencyTableType BuildContingencyTable(); + ContingencyTablePointerType BuildContingencyTable(); protected: ContingencyTableCalculator(); diff --git a/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.txx b/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.txx index 8f11d6207f..369ee1a3a0 100644 --- a/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.txx +++ b/Modules/Learning/Unsupervised/include/otbContingencyTableCalculator.txx @@ -83,7 +83,7 @@ ContingencyTableCalculator<TClassLabel> template<class TClassLabel> -typename ContingencyTableCalculator<TClassLabel>::ContingencyTableType +typename ContingencyTableCalculator<TClassLabel>::ContingencyTablePointerType ContingencyTableCalculator<TClassLabel> ::BuildContingencyTable() { @@ -113,11 +113,12 @@ ContingencyTableCalculator<TClassLabel> std::copy(refLabels.begin(), refLabels.end(), std::back_inserter(referenceLabels)); std::copy(prodLabels.begin(), prodLabels.end(), std::back_inserter(producedLabels)); - ContingencyTableType contingencyTable(referenceLabels, producedLabels); + ContingencyTablePointerType contingencyTable = ContingencyTableType::New(); + contingencyTable->SetLabels(referenceLabels, producedLabels); for( unsigned int i = 0; i < rows; ++i ) for( unsigned int j = 0; j < cols; ++j ) - contingencyTable.matrix(i,j) = m_LabelCount[referenceLabels[i]][producedLabels[j]]; + contingencyTable->matrix(i,j) = m_LabelCount[referenceLabels[i]][producedLabels[j]]; return contingencyTable; diff --git a/Modules/Learning/Unsupervised/test/otbContingencyTableCalculatorTest.cxx b/Modules/Learning/Unsupervised/test/otbContingencyTableCalculatorTest.cxx index b5ccae6bd7..dc0bdc8033 100644 --- a/Modules/Learning/Unsupervised/test/otbContingencyTableCalculatorTest.cxx +++ b/Modules/Learning/Unsupervised/test/otbContingencyTableCalculatorTest.cxx @@ -93,7 +93,8 @@ int otbContingencyTableCalculatorCompute(int argc, char* argv[]) typedef itk::FixedArray<ClassLabelType, 1> RLabelType; typedef itk::Statistics::ListSample<RLabelType> RListLabelType; typedef otb::ContingencyTableCalculator<ClassLabelType> CalculatorType; - typedef CalculatorType::ContingencyTableType ContingencyTableType; + typedef CalculatorType::ContingencyTableType ContingencyTableType; + typedef ContingencyTableType::Pointer ContingencyTablePointerType; CalculatorType::Pointer calculator = CalculatorType::New(); @@ -126,7 +127,7 @@ int otbContingencyTableCalculatorCompute(int argc, char* argv[]) } calculator->Compute( refLabels->Begin(), refLabels->End(), prodLabels->Begin(), prodLabels->End() ); - ContingencyTableType confmat = calculator->BuildContingencyTable(); + ContingencyTablePointerType contingencyTable = calculator->BuildContingencyTable(); if( static_cast<int>(calculator->GetNumberOfRefClasses()) != nbRefClasses ) @@ -148,7 +149,7 @@ int otbContingencyTableCalculatorCompute(int argc, char* argv[]) } - std::cout << "contingency table" << std::endl << confmat << std::endl; + std::cout << "contingency table" << std::endl << (*contingencyTable.GetPointer()) << std::endl; return EXIT_SUCCESS; } @@ -216,10 +217,10 @@ int otbContingencyTableCalculatorComputeWithBaseline(int itkNotUsed(argc), char* } calculator->Compute( refLabels->Begin(), refLabels->End(), prodLabels->Begin(), prodLabels->End() ); - CalculatorType::ContingencyTableType confmat = calculator->BuildContingencyTable(); + CalculatorType::ContingencyTablePointerType contingencyTable = calculator->BuildContingencyTable(); std::cout << std::endl; - std::cout << "contingency Table" << std::endl << confmat << std::endl; + std::cout << "contingency Table" << std::endl << (*contingencyTable.GetPointer()) << std::endl; unsigned int nbRefClasses = 5; unsigned int nbProdClasses = 7; -- GitLab