mlpack
diagonal_gmm_impl.hpp
Go to the documentation of this file.
1 
13 #ifndef MLPACK_METHODS_GMM_DIAGONAL_GMM_IMPL_HPP
14 #define MLPACK_METHODS_GMM_DIAGONAL_GMM_IMPL_HPP
15 
16 // In case it hasn't already been included.
17 #include "diagonal_gmm.hpp"
18 
19 namespace mlpack {
20 namespace gmm {
21 
23 template<typename FittingType>
24 double DiagonalGMM::Train(const arma::mat& observations,
25  const size_t trials,
26  const bool useExistingModel,
27  FittingType fitter)
28 {
29  double bestLikelihood; // This will be reported later.
30 
31  // We don't need to store temporary models if we are only doing one trial.
32  if (trials == 1)
33  {
34  // Train the model. The user will have been warned earlier if the
35  // DiagonalGMM was initialized with no parameters (0 gaussians,
36  // dimensionality of 0).
37  fitter.Estimate(observations, dists, weights, useExistingModel);
38  bestLikelihood = LogLikelihood(observations, dists, weights);
39  }
40  else
41  {
42  if (trials == 0)
43  return -DBL_MAX; // It's what they asked for...
44 
45  // If each trial must start from the same initial location,
46  // we must save it.
47  std::vector<distribution::DiagonalGaussianDistribution> distsOrig;
48  arma::vec weightsOrig;
49  if (useExistingModel)
50  {
51  distsOrig = dists;
52  weightsOrig = weights;
53  }
54 
55  // We need to keep temporary copies. We'll do the first training into the
56  // actual model position, so that if it's the best we don't need to
57  // copy it.
58  fitter.Estimate(observations, dists, weights, useExistingModel);
59  bestLikelihood = LogLikelihood(observations, dists, weights);
60 
61  Log::Info << "DiagonalGMM::Train(): Log-likelihood of trial 0 is "
62  << bestLikelihood << "." << std::endl;
63 
64  // Now the temporary model.
65  std::vector<distribution::DiagonalGaussianDistribution> distsTrial(
66  gaussians, distribution::DiagonalGaussianDistribution(dimensionality));
67  arma::vec weightsTrial(gaussians);
68 
69  for (size_t trial = 1; trial < trials; ++trial)
70  {
71  if (useExistingModel)
72  {
73  distsTrial = distsOrig;
74  weightsTrial = weightsOrig;
75  }
76 
77  fitter.Estimate(observations, distsTrial, weightsTrial,
78  useExistingModel);
79 
80  // Check to see if the log-likelihood of this one is better.
81  double newLikelihood = LogLikelihood(observations, distsTrial,
82  weightsTrial);
83 
84  Log::Info << "DiagonalGMM::Train(): Log-likelihood of trial " << trial
85  << " is " << newLikelihood << "." << std::endl;
86 
87  if (newLikelihood > bestLikelihood)
88  {
89  // Save new likelihood and copy new model.
90  bestLikelihood = newLikelihood;
91 
92  dists = distsTrial;
93  weights = weightsTrial;
94  }
95  }
96  }
97 
98  // Report final log-likelihood and return it.
99  Log::Info << "DiagonalGMM::Train(): log-likelihood of trained GMM is "
100  << bestLikelihood << "." << std::endl;
101  return bestLikelihood;
102 }
103 
108 template<typename FittingType>
109 double DiagonalGMM::Train(const arma::mat& observations,
110  const arma::vec& probabilities,
111  const size_t trials,
112  const bool useExistingModel,
113  FittingType fitter)
114 {
115  double bestLikelihood; // This will be reported later.
116 
117  // We don't need to store temporary models if we are only doing one trial.
118  if (trials == 1)
119  {
120  // Train the model. The user will have been warned earlier if the
121  // DiagonalGMM was initialized with no parameters (0 gaussians,
122  // dimensionality of 0).
123  fitter.Estimate(observations, probabilities, dists, weights,
124  useExistingModel);
125 
126  bestLikelihood = LogLikelihood(observations, dists, weights);
127  }
128  else
129  {
130  if (trials == 0)
131  return -DBL_MAX; // It's what they asked for...
132 
133  // If each trial must start from the same initial location, we must save it.
134  std::vector<distribution::DiagonalGaussianDistribution> distsOrig;
135  arma::vec weightsOrig;
136  if (useExistingModel)
137  {
138  distsOrig = dists;
139  weightsOrig = weights;
140  }
141 
142  // We need to keep temporary copies. We'll do the first training into the
143  // actual model position, so that if it's the best we don't need to copy it.
144  fitter.Estimate(observations, probabilities, dists, weights,
145  useExistingModel);
146 
147  bestLikelihood = LogLikelihood(observations, dists, weights);
148 
149  Log::Debug << "DiagonalGMM::Train(): Log-likelihood of trial 0 is "
150  << bestLikelihood << "." << std::endl;
151 
152  // Now the temporary model.
153  std::vector<distribution::DiagonalGaussianDistribution> distsTrial(
154  gaussians, distribution::DiagonalGaussianDistribution(dimensionality));
155  arma::vec weightsTrial(gaussians);
156 
157  for (size_t trial = 1; trial < trials; ++trial)
158  {
159  if (useExistingModel)
160  {
161  distsTrial = distsOrig;
162  weightsTrial = weightsOrig;
163  }
164 
165  fitter.Estimate(observations, probabilities, distsTrial, weightsTrial,
166  useExistingModel);
167 
168  // Check to see if the log-likelihood of this one is better.
169  double newLikelihood = LogLikelihood(observations, distsTrial,
170  weightsTrial);
171 
172  Log::Debug << "DiagonalGMM::Train(): Log-likelihood of trial " << trial
173  << " is " << newLikelihood << "." << std::endl;
174 
175  if (newLikelihood > bestLikelihood)
176  {
177  // Save new likelihood and copy new model.
178  bestLikelihood = newLikelihood;
179 
180  dists = distsTrial;
181  weights = weightsTrial;
182  }
183  }
184  }
185 
186  // Report final log-likelihood and return it.
187  Log::Info << "DiagonalGMM::Train(): log-likelihood of trained GMM is "
188  << bestLikelihood << "." << std::endl;
189  return bestLikelihood;
190 }
191 
193 template<typename Archive>
194 void DiagonalGMM::serialize(Archive& ar, const uint32_t /* version */)
195 {
196  ar(CEREAL_NVP(gaussians));
197  ar(CEREAL_NVP(dimensionality));
198  ar(CEREAL_NVP(dists));
199  ar(CEREAL_NVP(weights));
200 }
201 
202 } // namespace gmm
203 } // namespace mlpack
204 
205 #endif // MLPACK_METHODS_GMM_DIAGONAL_GMM_IMPL_HPP
static MLPACK_EXPORT util::NullOutStream Debug
MLPACK_EXPORT is required for global variables, so that they are properly exported by the Windows com...
Definition: log.hpp:79
Linear algebra utility functions, generally performed on matrices or vectors.
Definition: cv.hpp:1
void serialize(Archive &ar, const uint32_t)
Serialize the DiagonalGMM.
Definition: diagonal_gmm_impl.hpp:194
double Train(const arma::mat &observations, const size_t trials=1, const bool useExistingModel=false, FittingType fitter=FittingType())
Estimate the probability distribution directly from the given observations, using the given algorithm...
Definition: diagonal_gmm_impl.hpp:24
static MLPACK_EXPORT util::PrefixedOutStream Info
Prints informational messages if –verbose is specified, prefixed with [INFO ].
Definition: log.hpp:84
A single multivariate Gaussian distribution with diagonal covariance.
Definition: diagonal_gaussian_distribution.hpp:21