NormalizeComponentsZCA.h
Go to the documentation of this file.
1 //===========================================================================
2 /*!
3  *
4  *
5  * \brief Data normalization to zero mean, unit variance and zero covariance while keping the original coordinate system
6  *
7  *
8  *
9  *
10  * \author T. Glasmachers
11  * \date 2010
12  *
13  *
14  * \par Copyright 1995-2015 Shark Development Team
15  *
16  * <BR><HR>
17  * This file is part of Shark.
18  * <http://image.diku.dk/shark/>
19  *
20  * Shark is free software: you can redistribute it and/or modify
21  * it under the terms of the GNU Lesser General Public License as published
22  * by the Free Software Foundation, either version 3 of the License, or
23  * (at your option) any later version.
24  *
25  * Shark is distributed in the hope that it will be useful,
26  * but WITHOUT ANY WARRANTY; without even the implied warranty of
27  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
28  * GNU Lesser General Public License for more details.
29  *
30  * You should have received a copy of the GNU Lesser General Public License
31  * along with Shark. If not, see <http://www.gnu.org/licenses/>.
32  *
33  */
34 //===========================================================================
35 
36 
37 #ifndef SHARK_ALGORITHMS_TRAINERS_NORMALIZECOMPONENTSZCA_H
38 #define SHARK_ALGORITHMS_TRAINERS_NORMALIZECOMPONENTSZCA_H
39 
40 
43 #include <shark/Data/Statistics.h>
45 
46 namespace shark {
47 
48 
49 /// \brief Train a linear model to whiten the data
50 ///
51 /// ZCA does whitening in the sense that it sets the mean to zero and the covariance to the Identity.
52 /// However in contrast to NormalizeComponentsWhitening it makes sure that the initial and end coordinate
53 /// system are the same and just rescales the data. The effect is, that image data still resembles images
54 /// after applying ZCA in contrast to other methods which rotate the data randomly.
55 class NormalizeComponentsZCA : public AbstractUnsupervisedTrainer<LinearModel<RealVector> >
56 {
58 public:
59 
61  NormalizeComponentsZCA(double targetVariance = 1.0){
62  SHARK_CHECK(targetVariance > 0.0, "[NormalizeComponentsZCA::NormalizeComponentsZCA] target variance must be positive");
63  m_targetVariance = targetVariance;
64  }
65 
66  /// \brief From INameable: return the class name.
67  std::string name() const
68  { return "NormalizeComponentsZCA"; }
69 
70  void train(ModelType& model, UnlabeledData<RealVector> const& input){
71  std::size_t dc = dataDimension(input);
72  SHARK_CHECK(input.numberOfElements() >= dc + 1, "[NormalizeComponentsZCA::train] input needs to contain more points than there are input dimensions");
73  SHARK_CHECK(m_targetVariance > 0.0, "[NormalizeComponentsZCA::train] target variance must be positive");
74 
75  // dense model with bias having input and output dimension equal to data dimension
76  model.setStructure(dc, dc, true);
77 
78  RealVector mean;
79  RealMatrix covariance;
80  meanvar(input, mean, covariance);
81 
82  RealMatrix eigenvectors;
83  RealVector eigenvalues;
84  eigensymm(covariance, eigenvectors, eigenvalues);
85  covariance=RealMatrix();
86 
87  RealMatrix ZCAMatrix = eigenvectors;
88  for(std::size_t i=0; i<dc; i++) {
89  if(eigenvalues(i) > 0)
90  column(ZCAMatrix, i) /= std::sqrt(eigenvalues(i));
91  else
92  column(ZCAMatrix, i).clear();
93  }
94  ZCAMatrix = prod(ZCAMatrix,trans(eigenvectors));
95  ZCAMatrix *= std::sqrt(m_targetVariance);
96 
97  RealVector offset = -prod(ZCAMatrix,mean);
98 
99  model.setStructure(ZCAMatrix, offset);
100  }
101 };
102 
103 
104 }
105 #endif