gtsam
Loading...
Searching...
No Matches
DecisionTree.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
20#pragma once
21
22#include <gtsam/base/Testable.h>
23#include <gtsam/base/types.h>
25
26#if GTSAM_ENABLE_BOOST_SERIALIZATION
27#include <boost/serialization/nvp.hpp>
28#endif
29#include <memory>
30#include <functional>
31#include <iostream>
32#include <map>
33#include <set>
34#include <string>
35#include <utility>
36#include <vector>
37
38namespace gtsam {
39
61 template<typename L, typename Y>
63 protected:
65 static bool DefaultCompare(const Y& a, const Y& b) {
66 return a == b;
67 }
68
69 public:
70 using LabelFormatter = std::function<std::string(L)>;
71 using ValueFormatter = std::function<std::string(Y)>;
72 using CompareFunc = std::function<bool(const Y&, const Y&)>;
73
75 using Unary = std::function<Y(const Y&)>;
76 using UnaryAssignment = std::function<Y(const Assignment<L>&, const Y&)>;
77 using Binary = std::function<Y(const Y&, const Y&)>;
78
80 using LabelC = std::pair<L, size_t>;
81
83 struct Leaf;
84 struct Choice;
85
87 struct Node {
88 using Ptr = std::shared_ptr<Node>;
89
90#ifdef DT_DEBUG_MEMORY
91 static int nrNodes;
92#endif
93
94 // Constructor
95 Node() {
96#ifdef DT_DEBUG_MEMORY
97 std::cout << ++nrNodes << " constructed " << id() << std::endl;
98 std::cout.flush();
99#endif
100 }
101
102 // Destructor
103 virtual ~Node() {
104#ifdef DT_DEBUG_MEMORY
105 std::cout << --nrNodes << " destructed " << id() << std::endl;
106 std::cout.flush();
107#endif
108 }
109
110 // Unique ID for dot files
111 const void* id() const { return this; }
112
113 // everything else is virtual, no documentation here as internal
114 virtual void print(const std::string& s,
115 const LabelFormatter& labelFormatter,
116 const ValueFormatter& valueFormatter) const = 0;
117 virtual void dot(std::ostream& os, const LabelFormatter& labelFormatter,
118 const ValueFormatter& valueFormatter,
119 bool showZero) const = 0;
120 virtual bool sameLeaf(const Leaf& q) const = 0;
121 virtual bool sameLeaf(const Node& q) const = 0;
122 virtual bool equals(const Node& other, const CompareFunc& compare =
123 &DefaultCompare) const = 0;
124 virtual const Y& operator()(const Assignment<L>& x) const = 0;
125 virtual Ptr apply(const Unary& op) const = 0;
126 virtual Ptr apply(const UnaryAssignment& op,
127 const Assignment<L>& assignment) const = 0;
128 virtual Ptr apply_f_op_g(const Node&, const Binary&) const = 0;
129 virtual Ptr apply_g_op_fL(const Leaf&, const Binary&) const = 0;
130 virtual Ptr apply_g_op_fC(const Choice&, const Binary&) const = 0;
131 virtual Ptr choose(const L& label, size_t index) const = 0;
132 virtual bool isLeaf() const = 0;
133
134 private:
135#if GTSAM_ENABLE_BOOST_SERIALIZATION
137 friend class boost::serialization::access;
138 template <class ARCHIVE>
139 void serialize(ARCHIVE& ar, const unsigned int /*version*/) {}
140#endif
141 };
142
143
144 public:
146 using NodePtr = typename Node::Ptr;
147
150
151 protected:
156 template <typename It, typename ValueIt>
157 static NodePtr build(It begin, It end, ValueIt beginY, ValueIt endY);
158
164 template <typename It, typename ValueIt>
165 static NodePtr create(It begin, It end, ValueIt beginY, ValueIt endY);
166
176 template <typename X>
178 std::function<Y(const X&)> Y_of_X);
179
190 template <typename M, typename X>
192 std::function<L(const M&)> L_of_M,
193 std::function<Y(const X&)> Y_of_X);
194
195 public:
198
201
203 explicit DecisionTree(const Y& y);
204
212 DecisionTree(const L& label, const Y& y1, const Y& y2);
213
215 DecisionTree(const LabelC& label, const Y& y1, const Y& y2);
216
218 DecisionTree(const std::vector<LabelC>& labelCs, const std::vector<Y>& ys);
219
221 DecisionTree(const std::vector<LabelC>& labelCs, const std::string& table);
222
224 template<typename Iterator>
225 DecisionTree(Iterator begin, Iterator end, const L& label);
226
228 DecisionTree(const L& label, const DecisionTree& f0,
229 const DecisionTree& f1);
230
238 DecisionTree(const Unary& op, DecisionTree&& other) noexcept;
239
247 template <typename X, typename Func>
248 DecisionTree(const DecisionTree<L, X>& other, Func Y_of_X);
249
260 template <typename M, typename X, typename Func>
261 DecisionTree(const DecisionTree<M, X>& other, const std::map<M, L>& map,
262 Func Y_of_X);
263
267
275 void print(const std::string& s, const LabelFormatter& labelFormatter,
276 const ValueFormatter& valueFormatter) const;
277
278 // Testable
279 bool equals(const DecisionTree& other,
280 const CompareFunc& compare = &DefaultCompare) const;
281
285
287 virtual ~DecisionTree() = default;
288
290 bool empty() const { return !root_; }
291
293 bool operator==(const DecisionTree& q) const;
294
296 const Y& operator()(const Assignment<L>& x) const;
297
312 template <typename Func>
313 void visit(Func f) const;
314
329 template <typename Func>
330 void visitLeaf(Func f) const;
331
346 template <typename Func>
347 void visitWith(Func f) const;
348
350 size_t nrLeaves() const;
351
367 template <typename Func, typename X>
368 X fold(Func f, X x0) const;
369
371 std::set<L> labels() const;
372
374 DecisionTree apply(const Unary& op) const;
375
384 DecisionTree apply(const UnaryAssignment& op) const;
385
387 DecisionTree apply(const DecisionTree& g, const Binary& op) const;
388
391 DecisionTree choose(const L& label, size_t index) const {
392 NodePtr newRoot = root_->choose(label, index);
393 return DecisionTree(newRoot);
394 }
395
397 DecisionTree restrict(const Assignment<L>& assignment) const {
398 NodePtr newRoot = root_;
399 for (const auto& [l, v] : assignment) newRoot = newRoot->choose(l, v);
400 return DecisionTree(newRoot);
401 }
402
404 DecisionTree combine(const L& label, size_t cardinality,
405 const Binary& op) const;
406
408 DecisionTree combine(const LabelC& labelC, const Binary& op) const {
409 return combine(labelC.first, labelC.second, op);
410 }
411
413 void dot(std::ostream& os, const LabelFormatter& labelFormatter,
414 const ValueFormatter& valueFormatter, bool showZero = true) const;
415
417 void dot(const std::string& name, const LabelFormatter& labelFormatter,
418 const ValueFormatter& valueFormatter, bool showZero = true) const;
419
421 std::string dot(const LabelFormatter& labelFormatter,
422 const ValueFormatter& valueFormatter,
423 bool showZero = true) const;
424
433 template <typename A, typename B>
434 std::pair<DecisionTree<L, A>, DecisionTree<L, B>> split(
435 std::function<std::pair<A, B>(const Y&)> AB_of_Y) const;
436
439
440 // internal use only
441 explicit DecisionTree(const NodePtr& root);
442
443 // internal use only
444 template<typename Iterator> NodePtr
445 static compose(Iterator begin, Iterator end, const L& label);
446
448
449 private:
450#if GTSAM_ENABLE_BOOST_SERIALIZATION
452 friend class boost::serialization::access;
453 template <class ARCHIVE>
454 void serialize(ARCHIVE& ar, const unsigned int /*version*/) {
455 ar& BOOST_SERIALIZATION_NVP(root_);
456 }
457#endif
458 }; // DecisionTree
459
460 template <class L, class Y>
461 struct traits<DecisionTree<L, Y>> : public Testable<DecisionTree<L, Y>> {};
462
464
466 template<typename L, typename Y>
468 const typename DecisionTree<L, Y>::Unary& op) {
469 return f.apply(op);
470 }
471
473 template<typename L, typename Y>
475 const typename DecisionTree<L, Y>::UnaryAssignment& op) {
476 return f.apply(op);
477 }
478
480 template<typename L, typename Y>
482 const DecisionTree<L, Y>& g,
483 const typename DecisionTree<L, Y>::Binary& op) {
484 return f.apply(g, op);
485 }
486
493 template <typename L, typename T1, typename T2>
494 std::pair<DecisionTree<L, T1>, DecisionTree<L, T2> > unzip(
495 const DecisionTree<L, std::pair<T1, T2> >& input) {
496 return {
497 DecisionTree<L, T1>(input, [](std::pair<T1, T2> i) { return i.first; }),
498 DecisionTree<L, T2>(input, [](std::pair<T1, T2> i) { return i.second; })
499 };
500 }
501
502} // namespace gtsam
Typedefs for easier changing of types.
Concept check for values that can be used in unit tests.
An assignment from labels to a discrete value index (size_t).
Global functions in a separate testing namespace.
Definition chartTesting.h:28
std::pair< DecisionTree< L, T1 >, DecisionTree< L, T2 > > unzip(const DecisionTree< L, std::pair< T1, T2 > > &input)
unzip a DecisionTree with std::pair values.
Definition DecisionTree.h:494
DecisionTree< L, Y > apply(const DecisionTree< L, Y > &f, const typename DecisionTree< L, Y >::Unary &op)
free versions of apply
Definition DecisionTree.h:467
A manifold defines a space in which there is a notion of a linear tangent space that can be centered ...
Definition Group.h:37
A helper that implements the traits interface for GTSAM types.
Definition Testable.h:152
An assignment from labels to value index (size_t).
Definition Assignment.h:37
Definition DecisionTree-inl.h:53
Definition DecisionTree-inl.h:165
a decision tree is a function from assignments to values.
Definition DecisionTree.h:62
DecisionTree apply(const Unary &op) const
apply Unary operation "op" to f
Definition DecisionTree-inl.h:1006
static 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)
Convert from a DecisionTree<M, X> to DecisionTree<L, Y>.
Definition DecisionTree-inl.h:774
DecisionTree choose(const L &label, size_t index) const
create a new function where value(label)==index It's like "restrict" in Darwiche09book pg329,...
Definition DecisionTree.h:391
DecisionTree combine(const LabelC &labelC, const Binary &op) const
combine with LabelC for convenience
Definition DecisionTree.h:408
DecisionTree(Iterator begin, Iterator end, const L &label)
Create DecisionTree from others.
Definition DecisionTree-inl.h:555
virtual ~DecisionTree()=default
Make virtual.
static bool DefaultCompare(const Y &a, const Y &b)
Default method for comparison of two objects of type Y.
Definition DecisionTree.h:65
typename Node::Ptr NodePtr
Definition DecisionTree.h:146
DecisionTree(const std::vector< LabelC > &labelCs, const std::string &table)
Create from keys and string table.
Definition DecisionTree-inl.h:541
static NodePtr build(It begin, It end, ValueIt beginY, ValueIt endY)
Internal recursive function to create from keys, cardinalities, and Y values.
Definition DecisionTree-inl.h:694
std::set< L > labels() const
Retrieve all unique labels as a set.
Definition DecisionTree-inl.h:965
DecisionTree(const DecisionTree< L, X > &other, Func Y_of_X)
Convert from a different value type.
Definition DecisionTree-inl.h:603
DecisionTree apply(const DecisionTree &g, const Binary &op) const
apply binary operation "op" to f and g
Definition DecisionTree-inl.h:1031
bool empty() const
Check if tree is empty.
Definition DecisionTree.h:290
void visit(Func f) const
Visit all leaves in depth-first fashion.
Definition DecisionTree-inl.h:844
void visitLeaf(Func f) const
Visit all leaves in depth-first fashion.
Definition DecisionTree-inl.h:882
DecisionTree(const Unary &op, DecisionTree &&other) noexcept
Move constructor for DecisionTree.
Definition DecisionTree-inl.h:570
std::function< double(const double &)> Unary
Definition DecisionTree.h:75
DecisionTree(const Y &y)
Create a constant.
Definition DecisionTree-inl.h:505
DecisionTree apply(const UnaryAssignment &op) const
Apply Unary operation "op" to f while also providing the corresponding assignment.
Definition DecisionTree-inl.h:1018
X fold(Func f, X x0) const
Fold a binary function over the tree, returning accumulator.
Definition DecisionTree-inl.h:945
NodePtr root_
Definition DecisionTree.h:149
void print(const std::string &s, const LabelFormatter &labelFormatter, const ValueFormatter &valueFormatter) const
GTSAM-style print.
Definition DecisionTree-inl.h:984
DecisionTree combine(const L &label, size_t cardinality, const Binary &op) const
combine subtrees on key with binary operation "op"
Definition DecisionTree-inl.h:1055
std::string dot(const LabelFormatter &labelFormatter, const ValueFormatter &valueFormatter, bool showZero=true) const
output to graphviz format string
Definition DecisionTree-inl.h:1098
void visitWith(Func f) const
Visit all leaves in depth-first fashion.
Definition DecisionTree-inl.h:928
DecisionTree(const LabelC &label, const Y &y1, const Y &y2)
Allow Label+Cardinality for convenience.
Definition DecisionTree-inl.h:521
DecisionTree restrict(const Assignment< L > &assignment) const
Choose multiple values.
Definition DecisionTree.h:397
const Y & operator()(const Assignment< L > &x) const
evaluate
Definition DecisionTree-inl.h:997
void dot(std::ostream &os, const LabelFormatter &labelFormatter, const ValueFormatter &valueFormatter, bool showZero=true) const
output to graphviz format, stream version
Definition DecisionTree-inl.h:1067
std::pair< DecisionTree< L, A >, DecisionTree< L, B > > split(std::function< std::pair< A, B >(const Y &)> AB_of_Y) const
Convert into two trees with value types A and B.
Definition DecisionTree-inl.h:1109
static NodePtr convertFrom(const typename DecisionTree< L, X >::NodePtr &f, std::function< Y(const X &)> Y_of_X)
Convert from a DecisionTree<L, X> to DecisionTree<L, Y>.
Definition DecisionTree-inl.h:745
void dot(const std::string &name, const LabelFormatter &labelFormatter, const ValueFormatter &valueFormatter, bool showZero=true) const
output to graphviz format, open a file
Definition DecisionTree-inl.h:1077
DecisionTree(const DecisionTree< M, X > &other, const std::map< M, L > &map, Func Y_of_X)
Convert from a different value type X to value type Y, also translate labels via map from type M to L...
Definition DecisionTree-inl.h:611
DecisionTree(const std::vector< LabelC > &labelCs, const std::vector< Y > &ys)
Create from keys and a corresponding vector of values.
Definition DecisionTree-inl.h:533
bool operator==(const DecisionTree &q) const
equality
Definition DecisionTree-inl.h:991
std::pair< L, size_t > LabelC
Definition DecisionTree.h:80
DecisionTree(const L &label, const Y &y1, const Y &y2)
Create tree with 2 assignments y1, y2, splitting on variable label.
Definition DecisionTree-inl.h:511
size_t nrLeaves() const
Return the number of leaves in the tree.
Definition DecisionTree-inl.h:935
static NodePtr create(It begin, It end, ValueIt beginY, ValueIt endY)
Internal helper function to create a tree from keys, cardinalities, and Y values.
Definition DecisionTree-inl.h:736
DecisionTree()
Default constructor (for serialization).
Definition DecisionTree-inl.h:497
DecisionTree(const L &label, const DecisionTree &f0, const DecisionTree &f1)
Create DecisionTree from two others.
Definition DecisionTree-inl.h:562