GteApprGaussian2.h
Go to the documentation of this file.
1 // David Eberly, Geometric Tools, Redmond WA 98052
2 // Copyright (c) 1998-2017
3 // Distributed under the Boost Software License, Version 1.0.
4 // http://www.boost.org/LICENSE_1_0.txt
5 // http://www.geometrictools.com/License/Boost/LICENSE_1_0.txt
6 // File Version: 3.0.0 (2016/06/19)
7 
8 #pragma once
9 
10 #include <Mathematics/GteVector2.h>
14 
15 // Fit points with a Gaussian distribution. The center is the mean of the
16 // points, the axes are the eigenvectors of the covariance matrix, and the
17 // extents are the eigenvalues of the covariance matrix and are returned in
18 // increasing order. An oriented box is used to store the mean, axes, and
19 // extents.
20 
21 namespace gte
22 {
23 
24 template <typename Real>
26  :
27  public ApprQuery<Real, ApprGaussian2<Real>, Vector2<Real>>
28 {
29 public:
30  // Initialize the model parameters to zero.
31  ApprGaussian2();
32 
33  // Basic fitting algorithm.
34  bool Fit(int numPoints, Vector2<Real> const* points);
35  OrientedBox2<Real> const& GetParameters() const;
36 
37  // Functions called by ApprQuery::RANSAC. See GteApprQuery.h for a
38  // detailed description.
39  int GetMinimumRequired() const;
40  Real Error(Vector2<Real> const& observation) const;
41  bool Fit(std::vector<Vector2<Real>> const& observations,
42  std::vector<int> const& indices);
43 
44 private:
46 };
47 
48 
49 template <typename Real>
51 {
53  mParameters.axis[0] = Vector2<Real>::Zero();
54  mParameters.axis[1] = Vector2<Real>::Zero();
56 }
57 
58 template <typename Real>
59 bool ApprGaussian2<Real>::Fit(int numPoints, Vector2<Real> const* points)
60 {
61  if (numPoints >= GetMinimumRequired() && points)
62  {
63  // Compute the mean of the points.
65  for (int i = 0; i < numPoints; ++i)
66  {
67  mean += points[i];
68  }
69  Real invSize = ((Real)1) / (Real)numPoints;
70  mean *= invSize;
71 
72  // Compute the covariance matrix of the points.
73  Real covar00 = (Real)0, covar01 = (Real)0, covar11 = (Real)0;
74  for (int i = 0; i < numPoints; ++i)
75  {
76  Vector2<Real> diff = points[i] - mean;
77  covar00 += diff[0] * diff[0];
78  covar01 += diff[0] * diff[1];
79  covar11 += diff[1] * diff[1];
80  }
81  covar00 *= invSize;
82  covar01 *= invSize;
83  covar11 *= invSize;
84 
85  // Solve the eigensystem.
87  std::array<Real, 2> eval;
88  std::array<std::array<Real, 2>, 2> evec;
89  es(covar00, covar01, covar11, +1, eval, evec);
90  mParameters.center = mean;
91  mParameters.axis[0] = evec[0];
92  mParameters.axis[1] = evec[1];
93  mParameters.extent = eval;
94  return true;
95  }
96 
98  mParameters.axis[0] = Vector2<Real>::Zero();
99  mParameters.axis[1] = Vector2<Real>::Zero();
100  mParameters.extent = Vector2<Real>::Zero();
101  return false;
102 }
103 
104 template <typename Real>
106 {
107  return mParameters;
108 }
109 
110 template <typename Real>
112 {
113  return 2;
114 }
115 
116 template <typename Real>
118  std::vector<Vector2<Real>> const& observations,
119  std::vector<int> const& indices)
120 {
121  if (static_cast<int>(indices.size()) >= GetMinimumRequired())
122  {
123  // Compute the mean of the points.
125  for (auto index : indices)
126  {
127  mean += observations[index];
128  }
129  Real invSize = ((Real)1) / (Real)indices.size();
130  mean *= invSize;
131 
132  // Compute the covariance matrix of the points.
133  Real covar00 = (Real)0, covar01 = (Real)0, covar11 = (Real)0;
134  for (auto index : indices)
135  {
136  Vector2<Real> diff = observations[index] - mean;
137  covar00 += diff[0] * diff[0];
138  covar01 += diff[0] * diff[1];
139  covar11 += diff[1] * diff[1];
140  }
141  covar00 *= invSize;
142  covar01 *= invSize;
143  covar11 *= invSize;
144 
145  // Solve the eigensystem.
147  std::array<Real, 2> eval;
148  std::array<std::array<Real, 2>, 2> evec;
149  es(covar00, covar01, covar11, +1, eval, evec);
150  mParameters.center = mean;
151  mParameters.axis[0] = evec[0];
152  mParameters.axis[1] = evec[1];
153  mParameters.extent = eval;
154  }
155 
156  mParameters.center = Vector2<Real>::Zero();
157  mParameters.axis[0] = Vector2<Real>::Zero();
158  mParameters.axis[1] = Vector2<Real>::Zero();
159  mParameters.extent = Vector2<Real>::Zero();
160  return false;
161 }
162 
163 template <typename Real>
164 Real ApprGaussian2<Real>::Error(Vector2<Real> const& observation) const
165 {
166  Vector2<Real> diff = observation - mParameters.center;
167  Real error = (Real)0;
168  for (int i = 0; i < 2; ++i)
169  {
170  if (mParameters.extent[i] >(Real)0)
171  {
172  Real ratio = Dot(diff, mParameters.axis[i]) /
173  mParameters.extent[i];
174  error += ratio * ratio;
175  }
176  }
177  return error;
178 }
179 
180 
181 }
bool Fit(int numPoints, Vector2< Real > const *points)
OrientedBox2< Real > const & GetParameters() const
GLfixed GLfixed GLint GLint GLfixed points
Definition: glext.h:4927
GLsizei GLenum const void * indices
Definition: glcorearb.h:401
static Vector Zero()
int GetMinimumRequired() const
DualQuaternion< Real > Dot(DualQuaternion< Real > const &d0, DualQuaternion< Real > const &d1)
OrientedBox2< Real > mParameters
Real Error(Vector2< Real > const &observation) const
GLuint index
Definition: glcorearb.h:781


geometric_tools_engine
Author(s): Yijiang Huang
autogenerated on Thu Jul 18 2019 03:59:59