DiscreteFactor.cpp
Go to the documentation of this file.
1 /* ----------------------------------------------------------------------------
2 
3  * GTSAM Copyright 2010, Georgia Tech Research Corporation,
4  * Atlanta, Georgia 30332-0415
5  * All Rights Reserved
6  * Authors: Frank Dellaert, et al. (see THANKS for the full author list)
7 
8  * See LICENSE for the license information
9 
10  * -------------------------------------------------------------------------- */
11 
20 #include <gtsam/base/Vector.h>
23 
24 #include <cmath>
25 #include <sstream>
26 
27 using namespace std;
28 
29 namespace gtsam {
30 
31 /* ************************************************************************ */
32 DiscreteKeys DiscreteFactor::discreteKeys() const {
34  for (auto&& key : keys()) {
35  DiscreteKey dkey(key, cardinality(key));
36  if (std::find(result.begin(), result.end(), dkey) == result.end()) {
37  result.push_back(dkey);
38  }
39  }
40  return result;
41 }
42 
43 /* ************************************************************************* */
45  return -std::log((*this)(values));
46 }
47 
48 /* ************************************************************************* */
49 double DiscreteFactor::error(const HybridValues& c) const {
50  return this->error(c.discrete());
51 }
52 
53 /* ************************************************************************ */
54 AlgebraicDecisionTree<Key> DiscreteFactor::errorTree() const {
55  // Get all possible assignments
56  DiscreteKeys dkeys = discreteKeys();
57  // Reverse to make cartesian product output a more natural ordering.
58  DiscreteKeys rdkeys(dkeys.rbegin(), dkeys.rend());
59  const auto assignments = DiscreteValues::CartesianProduct(rdkeys);
60 
61  // Construct vector with error values
62  std::vector<double> errors;
63  for (const auto& assignment : assignments) {
64  errors.push_back(error(assignment));
65  }
66  return AlgebraicDecisionTree<Key>(dkeys, errors);
67 }
68 
69 /* ************************************************************************* */
70 std::vector<double> expNormalize(const std::vector<double>& logProbs) {
71  double maxLogProb = -std::numeric_limits<double>::infinity();
72  for (size_t i = 0; i < logProbs.size(); i++) {
73  double logProb = logProbs[i];
74  if ((logProb != std::numeric_limits<double>::infinity()) &&
75  logProb > maxLogProb) {
76  maxLogProb = logProb;
77  }
78  }
79 
80  // After computing the max = "Z" of the log probabilities L_i, we compute
81  // the log of the normalizing constant, log S, where S = sum_j exp(L_j - Z).
82  double total = 0.0;
83  for (size_t i = 0; i < logProbs.size(); i++) {
84  double probPrime = exp(logProbs[i] - maxLogProb);
85  total += probPrime;
86  }
87  double logTotal = log(total);
88 
89  // Now we compute the (normalized) probability (for each i):
90  // p_i = exp(L_i - Z - log S)
91  double checkNormalization = 0.0;
92  std::vector<double> probs;
93  for (size_t i = 0; i < logProbs.size(); i++) {
94  double prob = exp(logProbs[i] - maxLogProb - logTotal);
95  probs.push_back(prob);
96  checkNormalization += prob;
97  }
98 
99  // Numerical tolerance for floating point comparisons
100  double tol = 1e-9;
101 
102  if (!gtsam::fpEqual(checkNormalization, 1.0, tol)) {
103  std::string errMsg =
104  std::string("expNormalize failed to normalize probabilities. ") +
105  std::string("Expected normalization constant = 1.0. Got value: ") +
106  std::to_string(checkNormalization) +
107  std::string(
108  "\n This could have resulted from numerical overflow/underflow.");
109  throw std::logic_error(errMsg);
110  }
111  return probs;
112 }
113 
114 } // namespace gtsam
gtsam::HybridValues
Definition: HybridValues.h:37
Vector.h
typedef and functions to augment Eigen's VectorXd
e
Array< double, 1, 3 > e(1./3., 0.5, 2.)
keys
const KeyVector keys
Definition: testRegularImplicitSchurFactor.cpp:40
c
Scalar Scalar * c
Definition: benchVecAdd.cpp:17
different_sigmas::values
HybridValues values
Definition: testHybridBayesNet.cpp:245
log
const EIGEN_DEVICE_FUNC LogReturnType log() const
Definition: ArrayCwiseUnaryOps.h:128
gtsam::DiscreteKeys
DiscreteKeys is a set of keys that can be assembled using the & operator.
Definition: DiscreteKey.h:41
exp
const EIGEN_DEVICE_FUNC ExpReturnType exp() const
Definition: ArrayCwiseUnaryOps.h:97
result
Values result
Definition: OdometryOptimize.cpp:8
gtsam::AlgebraicDecisionTree< Key >
DiscreteFactor.h
gtsam::fpEqual
bool fpEqual(double a, double b, double tol, bool check_relative_also)
Definition: Vector.cpp:41
key
const gtsam::Symbol key('X', 0)
gtsam
traits
Definition: SFMdata.h:40
error
static double error
Definition: testRot3.cpp:37
gtsam::DiscreteValues
Definition: DiscreteValues.h:34
gtsam::DiscreteKey
std::pair< Key, size_t > DiscreteKey
Definition: DiscreteKey.h:38
std
Definition: BFloat16.h:88
gtsam::HybridValues::discrete
const DiscreteValues & discrete() const
Return the discrete values.
Definition: HybridValues.cpp:57
gtsam::expNormalize
std::vector< double > expNormalize(const std::vector< double > &logProbs)
Normalize a set of log probabilities.
Definition: DiscreteFactor.cpp:70
gtsam::tol
const G double tol
Definition: Group.h:79
HybridValues.h
i
int i
Definition: BiCGSTAB_step_by_step.cpp:9


gtsam
Author(s):
autogenerated on Sat Nov 16 2024 04:02:13