gtsam 4.2.0
gtsam
AlgebraicDecisionTree.h
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
19#pragma once
20
21#include <gtsam/base/Testable.h>
22#include <gtsam/discrete/DecisionTree-inl.h>
23
24#include <algorithm>
25#include <map>
26#include <string>
27#include <vector>
28namespace gtsam {
29
37 template <typename L>
38 class GTSAM_EXPORT AlgebraicDecisionTree : public DecisionTree<L, double> {
46 static std::string DefaultFormatter(const L& x) {
47 std::stringstream ss;
48 ss << x;
49 return ss.str();
50 }
51
52 public:
54
56 struct Ring {
57 static inline double zero() { return 0.0; }
58 static inline double one() { return 1.0; }
59 static inline double add(const double& a, const double& b) {
60 return a + b;
61 }
62 static inline double max(const double& a, const double& b) {
63 return std::max(a, b);
64 }
65 static inline double mul(const double& a, const double& b) {
66 return a * b;
67 }
68 static inline double div(const double& a, const double& b) {
69 return a / b;
70 }
71 static inline double id(const double& x) { return x; }
72 };
73
74 AlgebraicDecisionTree(double leaf = 1.0) : Base(leaf) {}
75
76 // Explicitly non-explicit constructor
77 AlgebraicDecisionTree(const Base& add) : Base(add) {}
78
80 AlgebraicDecisionTree(const L& label, double y1, double y2)
81 : Base(label, y1, y2) {}
82
84 AlgebraicDecisionTree(const typename Base::LabelC& labelC, double y1,
85 double y2)
86 : Base(labelC, y1, y2) {}
87
90 (const std::vector<typename Base::LabelC>& labelCs,
91 const std::vector<double>& ys) {
92 this->root_ =
93 Base::create(labelCs.begin(), labelCs.end(), ys.begin(), ys.end());
94 }
95
98 (const std::vector<typename Base::LabelC>& labelCs,
99 const std::string& table) {
100 // Convert string to doubles
101 std::vector<double> ys;
102 std::istringstream iss(table);
103 std::copy(std::istream_iterator<double>(iss),
104 std::istream_iterator<double>(), std::back_inserter(ys));
105
106 // now call recursive Create
107 this->root_ =
108 Base::create(labelCs.begin(), labelCs.end(), ys.begin(), ys.end());
109 }
110
112 template <typename Iterator>
113 AlgebraicDecisionTree(Iterator begin, Iterator end, const L& label)
114 : Base(nullptr) {
115 this->root_ = compose(begin, end, label);
116 }
117
124 template <typename M>
126 const std::map<M, L>& map) {
127 // Functor for label conversion so we can use `convertFrom`.
128 std::function<L(const M&)> L_of_M = [&map](const M& label) -> L {
129 return map.at(label);
130 };
131 std::function<double(const double&)> op = Ring::id;
132 this->root_ = DecisionTree<L, double>::convertFrom(other.root_, L_of_M, op);
133 }
134
137 return this->apply(g, &Ring::add);
138 }
139
142 return this->apply(g, &Ring::mul);
143 }
144
147 return this->apply(g, &Ring::div);
148 }
149
151 AlgebraicDecisionTree sum(const L& label, size_t cardinality) const {
152 return this->combine(label, cardinality, &Ring::add);
153 }
154
156 AlgebraicDecisionTree sum(const typename Base::LabelC& labelC) const {
157 return this->combine(labelC, &Ring::add);
158 }
159
161 void print(const std::string& s = "",
162 const typename Base::LabelFormatter& labelFormatter =
163 &DefaultFormatter) const {
164 auto valueFormatter = [](const double& v) {
165 return (boost::format("%4.8g") % v).str();
166 };
167 Base::print(s, labelFormatter, valueFormatter);
168 }
169
171 bool equals(const AlgebraicDecisionTree& other, double tol = 1e-9) const {
172 // lambda for comparison of two doubles upto some tolerance.
173 auto compare = [tol](double a, double b) {
174 return std::abs(a - b) < tol;
175 };
176 return Base::equals(other, compare);
177 }
178 };
179
180template <typename T>
182 : public Testable<AlgebraicDecisionTree<T>> {};
183} // namespace gtsam
Concept check for values that can be used in unit tests.
Global functions in a separate testing namespace.
Definition: chartTesting.h:28
void print(const Matrix &A, const string &s, ostream &stream)
print without optional string, must specify cout yourself
Definition: Matrix.cpp:156
DecisionTree< L, Y > apply(const DecisionTree< L, Y > &f, const typename DecisionTree< L, Y >::Unary &op)
free versions of apply
Definition: DecisionTree.h:392
A manifold defines a space in which there is a notion of a linear tangent space that can be centered ...
Definition: concepts.h:30
A helper that implements the traits interface for GTSAM types.
Definition: Testable.h:151
Algebraic Decision Trees fix the range to double Just has some nice constructors and some syntactic s...
Definition: AlgebraicDecisionTree.h:38
AlgebraicDecisionTree operator/(const AlgebraicDecisionTree &g) const
division
Definition: AlgebraicDecisionTree.h:146
AlgebraicDecisionTree sum(const L &label, size_t cardinality) const
sum out variable
Definition: AlgebraicDecisionTree.h:151
AlgebraicDecisionTree(const typename Base::LabelC &labelC, double y1, double y2)
Create a new leaf function splitting on a variable.
Definition: AlgebraicDecisionTree.h:84
void print(const std::string &s="", const typename Base::LabelFormatter &labelFormatter=&DefaultFormatter) const
print method customized to value type double.
Definition: AlgebraicDecisionTree.h:161
AlgebraicDecisionTree sum(const typename Base::LabelC &labelC) const
sum out variable
Definition: AlgebraicDecisionTree.h:156
AlgebraicDecisionTree(const AlgebraicDecisionTree< M > &other, const std::map< M, L > &map)
Convert labels from type M to type L.
Definition: AlgebraicDecisionTree.h:125
AlgebraicDecisionTree(const L &label, double y1, double y2)
Create a new leaf function splitting on a variable.
Definition: AlgebraicDecisionTree.h:80
bool equals(const AlgebraicDecisionTree &other, double tol=1e-9) const
Equality method customized to value type double.
Definition: AlgebraicDecisionTree.h:171
AlgebraicDecisionTree operator+(const AlgebraicDecisionTree &g) const
sum
Definition: AlgebraicDecisionTree.h:136
AlgebraicDecisionTree operator*(const AlgebraicDecisionTree &g) const
product
Definition: AlgebraicDecisionTree.h:141
AlgebraicDecisionTree(Iterator begin, Iterator end, const L &label)
Create a new function splitting on a variable.
Definition: AlgebraicDecisionTree.h:113
The Real ring with addition and multiplication.
Definition: AlgebraicDecisionTree.h:56
Decision Tree L = label for variables Y = function range (any algebra), e.g., bool,...
Definition: DecisionTree.h:47
NodePtr convertFrom(const typename DecisionTree< M, X >::NodePtr &f, std::function< L(const M &)> L_of_M, std::function< Y(const X &)> Y_of_X) const
Convert from a DecisionTree<M, X> to DecisionTree<L, Y>.
Definition: DecisionTree-inl.h:671
NodePtr root_
A DecisionTree just contains the root. TODO(dellaert): make protected.
Definition: DecisionTree.h:132
std::pair< L, size_t > LabelC
A label annotated with cardinality.
Definition: DecisionTree.h:65