From dfc3280ce20b3f551c8eae763d06a8e93041f872 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?C=C3=A9dric=20Traizet?= <traizetc@cesbio.cnes.fr>
Date: Thu, 4 May 2017 14:47:26 +0200
Subject: [PATCH] trainer and dimreduc app working for simple autoencoders

---
 app/cbDimensionalityReduction.cxx        | 44 +++++++++++++-----------
 app/cbDimensionalityReductionTrainer.cxx | 17 +++++++--
 include/encode_filter.h                  |  9 ++---
 include/encode_filter.txx                |  8 ++---
 4 files changed, 47 insertions(+), 31 deletions(-)

diff --git a/app/cbDimensionalityReduction.cxx b/app/cbDimensionalityReduction.cxx
index d2b6666079..a539b66c13 100644
--- a/app/cbDimensionalityReduction.cxx
+++ b/app/cbDimensionalityReduction.cxx
@@ -12,6 +12,7 @@
 #include "encode_filter.h"
 
 #include "dummy_filter.h"
+#include "otbMultiChannelExtractROI.h"
 
 namespace otb
 {
@@ -32,7 +33,7 @@ public:
 		
 	typedef shark::Autoencoder< shark::TanhNeuron, shark::LinearNeuron> AutoencoderType;
 	using FilterType = EncodeFilter<image_type, AutoencoderType, shark::Normalizer<shark::RealVector>> ;
-
+	typedef otb::MultiChannelExtractROI<FloatVectorImageType::InternalPixelType, FloatVectorImageType::InternalPixelType> ExtractROIFilterType;
 	/** Standard macro */
 	itkNewMacro(Self);
 	itkTypeMacro(CbDimensionalityReduction, otb::Application);
@@ -51,7 +52,7 @@ private:
 
 		AddParameter(ParameterType_InputFilename, "normalizer", "Normalizer model file");
 		SetParameterDescription("normalizer", "A normalizer model file (produced by the cbDimensionalityReductionTrainer application).");
-
+		
 		AddParameter(ParameterType_OutputImage, "out",  "Output Image");
     		SetParameterDescription("out", "Output image");
 
@@ -61,36 +62,39 @@ private:
 	void DoUpdateParameters()
 	{
 	}
-	
+
 	void DoExecute()
 	{	
-		
 		std::cout << "Appli" << std::endl;
-		FloatVectorImageType::Pointer inImage = GetParameterImage("in");
+		image_type::Pointer inImage = GetParameterImage("in");
 		std::string encoderPath = GetParameterString("model");
 		std::string normalizerPath = GetParameterString("normalizer");
 		
-		filter = FilterType::New();
-		filter->SetAutoencoderModel(encoderPath);
-		filter->SetNormalizerModel(normalizerPath);
-		filter->SetInput(inImage);
-		//filter->Update();
-		SetParameterOutputImage("out", filter->GetOutput());
-/*
-
-		using DummyFilterType = DummyFilter<image_type> ;
-		DummyFilterType::Pointer dummy_filter = DummyFilterType::New(); // this filter simply copies the input image (do not need shark library)
-		dummy_filter->SetInput(GetParameterFloatVectorImage("in"));
-		dummy_filter->Update();
-		SetParameterOutputImage("out", dummy_filter->GetOutput());
-*/
+		
 
+		filter_dim_reduc = FilterType::New();
+		filter_dim_reduc->SetAutoencoderModel(encoderPath);
+		filter_dim_reduc->SetNormalizerModel(normalizerPath);
+		filter_dim_reduc->SetInput(inImage);
 		
+		//SetParameterOutputImage("out", filter_dim_reduc->GetOutput());
+
+		m_ExtractROIFilter = ExtractROIFilterType::New();
+		m_ExtractROIFilter->SetInput(filter_dim_reduc->GetOutput());
+		for (unsigned int idx = 1; idx <= filter_dim_reduc->GetDimension(); ++idx)
+		{
+		m_ExtractROIFilter->SetChannel(idx );
+		}
+
+		SetParameterOutputImage("out", m_ExtractROIFilter->GetOutput());
+
 		//SetParameterOutputImage("out", inImage); // copy input image
 
 	}
 
-	FilterType::Pointer filter;
+	FilterType::Pointer filter_dim_reduc;
+	ExtractROIFilterType::Pointer m_ExtractROIFilter;
+
 };
 }
 }
diff --git a/app/cbDimensionalityReductionTrainer.cxx b/app/cbDimensionalityReductionTrainer.cxx
index 7250e35ddd..2ceb73d902 100644
--- a/app/cbDimensionalityReductionTrainer.cxx
+++ b/app/cbDimensionalityReductionTrainer.cxx
@@ -99,7 +99,18 @@ private:
 	
 		AddParameter(ParameterType_StringList, "feat", "Field names to be calculated."); //
 		SetParameterDescription("feat","List of field names in the input vector data used as features for training."); //
+		
+		AddParameter(ParameterType_Int, "k","target dimension");
+		SetParameterDescription("k", "Dimension of the output feature vectors");
+
+		/*
+		AddParameter(ParameterType_InputFilename, "model", "Dimensionality Reduction model file");
+		SetParameterDescription("model", "A model file (produced by cbDimensionalityReduction application.");
 
+		AddParameter(ParameterType_InputFilename, "normalizer", "normalizer model file");
+		SetParameterDescription("normalizer", "A model file (produced by cbDimensionalityReduction application.");
+*/
+		
 /*
 		AddParameter(ParameterType_InputVectorData, "val", "Name of the input validation vector data");
 		SetParameterDescription("val","The vector data used for validation.");
@@ -141,9 +152,9 @@ private:
 		otb::Shark::ListSampleToSharkVector<ListSampleType>( input, features);
 		shark::Data<shark::RealVector> inputSamples = shark::createDataFromRange( features );
 		
-		std::size_t numHidden= 5;   // stoi convert string to int
-		std::size_t iterations = 10;
-		double regularisation = 0; // stod convert string to double
+		std::size_t numHidden= GetParameterInt("k");   
+		std::size_t iterations = 100;
+		double regularisation = 0; 
 		
 
 		shark::Normalizer<shark::RealVector> normalizer = trainNormalizer(inputSamples);
diff --git a/include/encode_filter.h b/include/encode_filter.h
index 9a6b70c117..6b5e361fb3 100644
--- a/include/encode_filter.h
+++ b/include/encode_filter.h
@@ -24,15 +24,15 @@ class ITK_EXPORT EncodeFilter:public itk::ImageToImageFilter< TImage, TImage >
 		void SetAutoencoderModel(const std::string encoderPath);
 		void SetNormalizerModel(const std::string NormalizerPath);
 		void SetModels( const AutoencoderModel net, const NormalizerModel normalizer);
-
+		std::size_t GetDimension(){return m_hidden_neuron;};
 	protected:
 		EncodeFilter();
 	  	~EncodeFilter(){}
-
+	
   		typename TImage::ConstPointer GetInputImage();
 		AutoencoderModel GetAutoencoderModel();
 		NormalizerModel GetNormalizerModel();
- 
+ 		
 	/** Does the real work. */
 
 		virtual void BeforeThreadedGenerateData();
@@ -42,7 +42,8 @@ class ITK_EXPORT EncodeFilter:public itk::ImageToImageFilter< TImage, TImage >
 	  	EncodeFilter(const Self &); //purposely not implemented
 	  	void operator=(const Self &);  //purposely not implemented
 	        AutoencoderModel m_net;  
-		NormalizerModel m_normalizer;
+		NormalizerModel m_normalizer;	
+		std::size_t m_hidden_neuron;
 };
  
 #ifndef ITK_MANUAL_INSTANTIATION
diff --git a/include/encode_filter.txx b/include/encode_filter.txx
index adb071854f..8e7b334a9a 100644
--- a/include/encode_filter.txx
+++ b/include/encode_filter.txx
@@ -37,6 +37,7 @@ void EncodeFilter<TImage, AutoencoderModel, NormalizerModel>::SetAutoencoderMode
 	boost::archive::polymorphic_text_iarchive ia(ifs);
 	m_net.read(ia);
 	ifs.close();
+	m_hidden_neuron = m_net.numberOfHiddenNeurons();
 }
 
 
@@ -101,15 +102,13 @@ this->SetNumberOfThreads(1);
 }
 
 
-/*template< class TImage, class AutoencoderModel, class NormalizerModel>
-void EncodeFilter<TImage, AutoencoderModel, NormalizerModel>::GenerateData()*/
+
 template< class TImage, class AutoencoderModel, class NormalizerModel>
 void EncodeFilter<TImage, AutoencoderModel, NormalizerModel>::ThreadedGenerateData(const typename TImage::RegionType &outputRegionForThread, unsigned int threadId)
 {
 	//Data_with_info info;
 	typename TImage::ConstPointer input = this->GetInput();
 	typename TImage::Pointer output = this->GetOutput();
- 	
 	// Image to vector
 	const unsigned int img_bands = input->GetNumberOfComponentsPerPixel();
 	
@@ -149,11 +148,12 @@ void EncodeFilter<TImage, AutoencoderModel, NormalizerModel>::ThreadedGenerateDa
 		for(unsigned int a = 0; a < numHidden; ++a){
 			pixelValue[a]=vect_out[a];
 		}
-
+		
 		imageIteratorOut.Set(pixelValue);
 		++imageIteratorOut;
 		++vect_it;
 	}
+	
 }
 	 
 
-- 
GitLab