28 #include <boost/optional.hpp>
29 #include <boost/foreach.hpp>
30 #include <boost/assign/list_of.hpp>
33 using boost::assign::cref_list_of;
38 template<
class CLIQUE>
42 getCliqueData(data, root);
47 template<
class CLIQUE>
49 data.conditionalSizes.push_back(clique->conditional()->nrFrontals());
50 data.separatorSizes.push_back(clique->conditional()->nrParents());
52 getCliqueData(data, c);
57 template<
class CLIQUE>
61 count += root->numCachedSeparatorMarginals();
66 template<
class CLIQUE>
68 if (roots_.empty())
throw std::invalid_argument(
"the root of Bayes tree has not been initialized!");
69 std::ofstream of(s.c_str());
72 saveGraph(of, root, keyFormatter);
78 template<
class CLIQUE>
82 std::stringstream out;
84 std::string parent = out.str();
85 parent +=
"[label=\"";
87 BOOST_FOREACH(
Key index, clique->conditional_->frontals()) {
88 if(!first) parent +=
","; first =
false;
89 parent += indexFormatter(index);
94 s << parentnum <<
"->" << num <<
"\n";
98 BOOST_FOREACH(
Key sep, clique->conditional_->parents()) {
99 if(!first) parent +=
","; first =
false;
100 parent += indexFormatter(sep);
108 saveGraph(s, c, indexFormatter, parentnum);
113 template<
class CLIQUE>
117 size += clique->treeSize();
122 template<
class CLIQUE>
124 BOOST_FOREACH(
Key j, clique->conditional()->frontals())
126 if (parent_clique != NULL) {
127 clique->parent_ = parent_clique;
128 parent_clique->children.push_back(clique);
130 roots_.push_back(clique);
137 template<
class FACTOR,
class CLIQUE>
143 template<
class FACTOR,
class CLIQUE>
144 struct _pushCliqueFunctor {
145 _pushCliqueFunctor(FactorGraph<FACTOR>& graph_) : graph(graph_) {}
146 FactorGraph<FACTOR>& graph;
147 int operator()(
const boost::shared_ptr<CLIQUE>& clique,
int dummy) {
148 graph.push_back(clique->conditional_);
155 template<
class CLIQUE>
160 _pushCliqueFunctor<FactorType,CLIQUE> functor(graph);
166 template<
class CLIQUE>
173 template<
typename NODE>
174 boost::shared_ptr<NODE>
175 BayesTreeCloneForestVisitorPre(
const boost::shared_ptr<NODE>& node,
const boost::shared_ptr<NODE>& parentPointer)
178 boost::shared_ptr<NODE> clone = boost::make_shared<NODE>(*node);
179 clone->children.
clear();
180 clone->parent_ = parentPointer;
181 parentPointer->children.push_back(clone);
187 template<
class CLIQUE>
190 boost::shared_ptr<Clique> rootContainer = boost::make_shared<Clique>();
192 BOOST_FOREACH(
const sharedClique& root, rootContainer->children) {
193 root->parent_ =
typename Clique::weak_ptr();
200 template<
class CLIQUE>
202 std::cout << s <<
": cliques: " << size() <<
", variables: " << nodes_.size() << std::endl;
208 template<
class CLIQUE>
209 bool check_sharedCliques(
213 return v1.first == v2.first &&
214 ((!v1.second && !v2.second) || (v1.second && v2.second && v1.second->equals(*v2.second)));
218 template<
class CLIQUE>
220 return size()==other.
size() &&
221 std::equal(nodes_.begin(), nodes_.end(), other.
nodes_.begin(), &check_sharedCliques<CLIQUE>);
225 template<
class CLIQUE>
226 template<
class CONTAINER>
228 typename CONTAINER::const_iterator lowestOrderedParent = min_element(parents.begin(), parents.end());
229 assert(lowestOrderedParent != parents.end());
230 return *lowestOrderedParent;
234 template<
class CLIQUE>
237 BOOST_FOREACH(
const Key& j, subtree->conditional()->frontals()) {
238 bool inserted = nodes_.insert(std::make_pair(j, subtree)).second;
239 assert(inserted); (void)inserted;
243 BOOST_FOREACH(
const sharedClique& child, subtree->children) {
244 fillNodesIndex(child); }
248 template<
class CLIQUE>
250 roots_.push_back(subtree);
251 fillNodesIndex(subtree);
257 template<
class CLIQUE>
258 typename BayesTree<CLIQUE>::sharedConditional
261 gttic(BayesTree_marginalFactor);
267 FactorGraphType cliqueMarginal = clique->marginal2(
function);
270 BayesNetType marginalBN = *cliqueMarginal.marginalMultifrontalBayesNet(
271 Ordering(cref_list_of<1,Key>(j)), boost::none,
function);
274 return marginalBN.front();
280 template<
class CLIQUE>
281 typename BayesTree<CLIQUE>::sharedFactorGraph
284 gttic(BayesTree_joint);
285 return boost::make_shared<FactorGraphType>(*jointBayesNet(j1, j2,
function));
289 template<
class CLIQUE>
290 typename BayesTree<CLIQUE>::sharedBayesNet
293 gttic(BayesTree_jointBayesNet);
297 gttic(Lowest_common_ancestor);
318 while(p1 != path1.end() && p2 != path2.end() && *p1 == *p2) {
324 gttoc(Lowest_common_ancestor);
327 FactorGraphType p_BC1C2;
333 FactorGraphType p_B = B->marginal2(
function);
337 gttic(Clique_shortcuts);
338 BayesNetType p_C1_Bred = C1->shortcut(B,
function);
339 BayesNetType p_C2_Bred = C2->shortcut(B,
function);
340 gttoc(Clique_shortcuts);
344 gttic(Full_root_factoring);
345 boost::shared_ptr<typename EliminationTraitsType::BayesTreeType> p_C1_B; {
347 FastSet<Key> C1_minus_B_set(C1->conditional()->beginParents(), C1->conditional()->endParents());
348 BOOST_FOREACH(
const Key j, *B->conditional()) {
349 C1_minus_B_set.erase(j); }
350 C1_minus_B.assign(C1_minus_B_set.begin(), C1_minus_B_set.end());
353 sharedFactorGraph temp_remaining;
354 boost::tie(p_C1_B, temp_remaining) =
355 FactorGraphType(p_C1_Bred).eliminatePartialMultifrontal(
Ordering(C1_minus_B),
function);
357 boost::shared_ptr<typename EliminationTraitsType::BayesTreeType> p_C2_B; {
359 FastSet<Key> C2_minus_B_set(C2->conditional()->beginParents(), C2->conditional()->endParents());
360 BOOST_FOREACH(
const Key j, *B->conditional()) {
361 C2_minus_B_set.erase(j); }
362 C2_minus_B.assign(C2_minus_B_set.begin(), C2_minus_B_set.end());
365 sharedFactorGraph temp_remaining;
366 boost::tie(p_C2_B, temp_remaining) =
367 FactorGraphType(p_C2_Bred).eliminatePartialMultifrontal(
Ordering(C2_minus_B),
function);
369 gttoc(Full_root_factoring);
371 gttic(Variable_joint);
376 p_BC1C2 += C1->conditional();
378 p_BC1C2 += C2->conditional();
379 gttoc(Variable_joint);
385 gttic(Disjoint_marginals);
386 p_BC1C2 += C1->marginal2(
function);
387 p_BC1C2 += C2->marginal2(
function);
388 gttoc(Disjoint_marginals);
392 return p_BC1C2.marginalMultifrontalBayesNet(
Ordering(cref_list_of<2,Key>(j1)(j2)), boost::none,
function);
396 template<
class CLIQUE>
404 template<
class CLIQUE>
407 root->deleteCachedShortcuts();
412 template<
class CLIQUE>
415 if (clique->isRoot()) {
416 typename Roots::iterator root = std::find(roots_.begin(), roots_.end(), clique);
417 if(root != roots_.end())
421 typename Roots::iterator child = std::find(parent->children.begin(), parent->children.end(), clique);
422 assert(child != parent->children.end());
423 parent->children.erase(child);
428 child->parent_ =
typename Clique::weak_ptr();
430 BOOST_FOREACH(
Key j, clique->conditional()->frontals()) {
431 nodes_.unsafe_erase(j);
436 template<
class CLIQUE>
443 orphans.remove(clique);
446 this->removeClique(clique);
449 this->removePath(
typename Clique::shared_ptr(clique->parent_.lock()), bn, orphans);
452 orphans.insert(orphans.begin(), clique->children.begin(), clique->children.end());
453 clique->children.clear();
455 bn.push_back(clique->conditional_);
461 template<
class CLIQUE>
465 BOOST_FOREACH(
const Key& j, keys)
469 typename Nodes::const_iterator node = nodes_.find(j);
470 if(node != nodes_.end()) {
472 this->removePath(node->second, bn, orphans);
479 orphan->deleteCachedShortcuts();
483 template<
class CLIQUE>
489 cliques.push_back(subtree);
492 if(!subtree->isRoot())
493 subtree->parent()->children.erase(std::find(
494 subtree->parent()->children.begin(), subtree->parent()->children.end(), subtree));
496 roots_.erase(std::find(roots_.begin(), roots_.end(), subtree));
499 for(
typename Cliques::iterator clique = cliques.begin(); clique != cliques.end(); ++clique)
502 BOOST_FOREACH(
const sharedClique& child, (*clique)->children) {
503 cliques.push_back(child); }
506 (*clique)->deleteCachedShortcutsNonRecursive();
509 BOOST_FOREACH(
Key j, (*clique)->conditional()->frontals()) {
510 nodes_.unsafe_erase(j); }
513 (*clique)->parent_.reset();
514 (*clique)->children.clear();
Nodes nodes_
Map from indices to Clique.
Definition: BayesTree.h:95
boost::shared_ptr< Clique > sharedClique
Shared pointer to a clique.
Definition: BayesTree.h:72
Definition: BayesTree.h:64
Bayes Tree is a tree of cliques of a Bayes Chain.
void fillNodesIndex(const sharedClique &subtree)
Fill the nodes index for a subtree.
Definition: BayesTree-inst.h:235
A factor graph is a bipartite graph with factor nodes connected to variable nodes.
Definition: BayesTree.h:32
void clear()
Remove all nodes.
Definition: BayesTree-inst.h:397
void addFactorsToGraph(FactorGraph< FactorType > &graph) const
Add all cliques in this BayesTree to the specified factor graph.
Definition: BayesTree-inst.h:156
size_t size() const
number of cliques
Definition: BayesTree-inst.h:114
BayesTree()
Create an empty Bayes Tree.
Definition: BayesTree.h:107
void DepthFirstForest(FOREST &forest, DATA &rootData, VISITOR_PRE &visitorPre, VISITOR_POST &visitorPost)
Traverse a forest depth-first with pre-order and post-order visits.
Definition: treeTraversal-inst.h:75
boost::enable_if< boost::is_base_of< FactorType, DERIVEDFACTOR > >::type push_back(boost::shared_ptr< DERIVEDFACTOR > factor)
Add a factor directly using a shared_ptr.
Definition: FactorGraph.h:155
void insertRoot(const sharedClique &subtree)
Insert a new subtree with known parent clique.
Definition: BayesTree-inst.h:249
void removePath(sharedClique clique, BayesNetType &bn, Cliques &orphans)
Remove path from clique to root and return that path as factors plus a list of orphaned subtree roots...
Definition: BayesTree-inst.h:437
store all the sizes
Definition: BayesTree.h:46
Cliques removeSubtree(const sharedClique &subtree)
Remove the requested subtree.
Definition: BayesTree-inst.h:484
sharedConditional marginalFactor(Key j, const Eliminate &function=EliminationTraitsType::DefaultEliminate) const
Return marginal on any variable.
Definition: BayesTree-inst.h:259
sharedFactorGraph joint(Key j1, Key j2, const Eliminate &function=EliminationTraitsType::DefaultEliminate) const
return joint on two variables Limitation: can only calculate joint if cliques are disjoint or one of ...
Definition: BayesTree-inst.h:282
Key findParentClique(const CONTAINER &parents) const
Find parent clique of a conditional.
Definition: BayesTree-inst.h:227
size_t Key
Integer nonlinear key type.
Definition: types.h:59
void removeClique(sharedClique clique)
remove a clique: warning, can result in a forest
Definition: BayesTree-inst.h:413
void removeTop(const FastVector< Key > &keys, BayesNetType &bn, Cliques &orphans)
Given a list of indices, turn "contaminated" part of the tree back into a factor graph.
Definition: BayesTree-inst.h:462
void print(const std::string &s="", const KeyFormatter &keyFormatter=DefaultKeyFormatter) const
print
Definition: BayesTree-inst.h:201
bool equal(const T &obj1, const T &obj2, double tol)
Call equal on the object.
Definition: Testable.h:75
sharedBayesNet jointBayesNet(Key j1, Key j2, const Eliminate &function=EliminationTraitsType::DefaultEliminate) const
return joint on two variables as a BayesNet Limitation: can only calculate joint if cliques are disjo...
Definition: BayesTree-inst.h:291
bool equals(const This &other, double tol=1e-9) const
check equality
Definition: BayesTree-inst.h:219
void deleteCachedShortcuts()
Clear all shortcut caches - use before timing on marginal calculation to avoid residual cache data...
Definition: BayesTree-inst.h:405
BayesTreeCliqueData getCliqueData() const
Gather data on all cliques.
Definition: BayesTree-inst.h:39
Definition: Ordering.h:30
size_t numCachedSeparatorMarginals() const
Collect number of cliques with cached separator marginals.
Definition: BayesTree-inst.h:58
Definition: FastList.h:38
void addClique(const sharedClique &clique, const sharedClique &parent_clique=sharedClique())
add a clique (top down)
Definition: BayesTree-inst.h:123
void saveGraph(const std::string &s, const KeyFormatter &keyFormatter=DefaultKeyFormatter) const
Read only with side effects.
Definition: BayesTree-inst.h:67
void PrintForest(const FOREST &forest, std::string str, const KeyFormatter &keyFormatter)
Print a tree, prefixing each line with str, and formatting keys using keyFormatter.
Definition: treeTraversal-inst.h:218
This & operator=(const This &other)
Assignment operator.
Definition: BayesTree-inst.h:188
boost::function< std::string(Key)> KeyFormatter
Typedef for a function to format a key, i.e. to convert it to a string.
Definition: types.h:62