OTB  9.0.0
Orfeo Toolbox
otbNAPCAImageFilter.hxx
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2005-2022 Centre National d'Etudes Spatiales (CNES)
3  *
4  * This file is part of Orfeo Toolbox
5  *
6  * https://www.orfeo-toolbox.org/
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  */
20 
21 #ifndef otbNAPCAImageFilter_hxx
22 #define otbNAPCAImageFilter_hxx
23 #include "otbNAPCAImageFilter.h"
24 
25 #include "itkMacro.h"
26 
27 #include <vnl/vnl_matrix.h>
28 #include <vnl/algo/vnl_matrix_inverse.h>
29 #include <vnl/algo/vnl_symmetric_eigensystem.h>
30 #include <vnl/algo/vnl_generalized_eigensystem.h>
31 
32 namespace otb
33 {
34 
35 template <class TInputImage, class TOutputImage, class TNoiseImageFilter, Transform::TransformDirection TDirectionOfTransformation>
37 {
38  InternalMatrixType An = this->GetNoiseCovarianceMatrix().GetVnlMatrix();
40  vnl_vector<double> vectValPn;
41  vnl_symmetric_eigensystem_compute(An, Fn, vectValPn);
42 
43  /* We used normalized PCA */
44  InternalMatrixType valPn(vectValPn.size(), vectValPn.size(), vnl_matrix_null);
45  for (unsigned int i = 0; i < valPn.rows(); ++i)
46  {
47  if (vectValPn[i] > 0.)
48  {
49  valPn(i, i) = 1. / std::sqrt(vectValPn[i]);
50  }
51  else if (vectValPn[i] < 0.)
52  {
53  otbMsgDebugMacro(<< "ValPn(" << i << ") neg : " << vectValPn[i] << " taking abs value");
54  valPn(i, i) = 1. / std::sqrt(std::abs(vectValPn[i]));
55  }
56  else
57  {
58  throw itk::ExceptionObject(__FILE__, __LINE__, "Null Eigen value !!", ITK_LOCATION);
59  }
60  }
61  Fn = Fn * valPn;
62 
63  InternalMatrixType Ax = vnl_matrix_inverse<MatrixElementType>(this->GetCovarianceMatrix().GetVnlMatrix());
64  InternalMatrixType Aadj = Fn.transpose() * Ax * Fn;
65 
66  InternalMatrixType Fadj;
67  vnl_vector<double> vectValPadj;
68  vnl_symmetric_eigensystem_compute(Aadj, Fadj, vectValPadj);
69 
70  InternalMatrixType transf = Fn * Fadj;
71  transf.inplace_transpose();
72 
73  if (this->GetNumberOfPrincipalComponentsRequired() != this->GetInput()->GetNumberOfComponentsPerPixel())
74  this->m_TransformationMatrix = transf.get_n_rows(0, this->GetNumberOfPrincipalComponentsRequired());
75  else
76  this->m_TransformationMatrix = transf;
77 
78  this->m_EigenValues.SetSize(this->GetNumberOfPrincipalComponentsRequired());
79  for (unsigned int i = 0; i < this->GetNumberOfPrincipalComponentsRequired(); ++i)
80  this->m_EigenValues[this->GetNumberOfPrincipalComponentsRequired() - 1 - i] = static_cast<RealType>(vectValPadj[i]);
81 }
82 
83 
84 } // end of namespace otb
85 
86 #endif
otb
The "otb" namespace contains all Orfeo Toolbox (OTB) classes.
Definition: otbJoinContainer.h:32
otbNAPCAImageFilter.h
otb::MNFImageFilter::InternalMatrixType
MatrixType::InternalMatrixType InternalMatrixType
Definition: otbMNFImageFilter.h:82
otb::MNFImageFilter::RealType
CovarianceEstimatorFilterType::RealType RealType
Definition: otbMNFImageFilter.h:78
otbMsgDebugMacro
#define otbMsgDebugMacro(x)
Definition: otbMacro.h:62
otb::NAPCAImageFilter::GenerateTransformationMatrix
void GenerateTransformationMatrix() override
Definition: otbNAPCAImageFilter.hxx:36