如何在boost中访问rbtree的根

如何在boost中访问rbtree的根,boost,Boost,基于实例实现了一个红黑树。但是我不明白标题的意思,它是树的根吗?根据描述: 标题节点不仅与根节点保持链接,还与树的最左侧节点保持链接,以启用常数时间开始(),并与树的最右侧节点保持链接,以在与通用集合算法(集合联合等)一起使用时启用线性时间性能 如何使用头节点访问树的根?这有多复杂?Boost Intrusive的RBTree实现中的头节点包含指向根节点、最左侧和最右侧节点的链接(请参阅) 因此,parent\uu是指向根节点的指针 您可以使用基于该示例中显示的“算法策略”的容器抽象。你会这样写

基于实例实现了一个红黑树。但是我不明白标题的意思,它是树的根吗?根据描述:

标题节点不仅与根节点保持链接,还与树的最左侧节点保持链接,以启用常数时间开始(),并与树的最右侧节点保持链接,以在与通用集合算法(集合联合等)一起使用时启用线性时间性能


如何使用头节点访问树的根?这有多复杂?

Boost Intrusive的RBTree实现中的头节点包含指向根节点、最左侧和最右侧节点的链接(请参阅)

因此,
parent\uu
是指向根节点的指针

您可以使用基于该示例中显示的“算法策略”的容器抽象。你会这样写,就像我在上一个答案中链接的那样:

下面是一个简单、自包含的示例,演示如何使用基于节点类型构建的实际
rbtree
容器(而不仅仅是算法)

请注意,您仍然可以使用容器特性“钻取”并获取节点

struct my_node
{
    my_node(int i = 0) :
        parent_(nullptr),
        left_  (nullptr),
        right_ (nullptr),
        int_   (i)
    { }

    my_node *parent_, *left_, *right_;
    int      color_;
    //data members
    int      int_;

    bool operator<(my_node const& other) const { return int_ < other.int_; }
};

//Define our own rbtree_node_traits
struct my_rbtree_node_traits
{
   typedef my_node                                    node;
   typedef my_node *                                  node_ptr;
   typedef const my_node *                            const_node_ptr;
   typedef int                                        color;
   static node_ptr get_parent(const_node_ptr n)       {  return n->parent_;   }
   static void set_parent(node_ptr n, node_ptr parent){  n->parent_ = parent; }
   static node_ptr get_left(const_node_ptr n)         {  return n->left_;     }
   static void set_left(node_ptr n, node_ptr left)    {  n->left_ = left;     }
   static node_ptr get_right(const_node_ptr n)        {  return n->right_;    }
   static void set_right(node_ptr n, node_ptr right)  {  n->right_ = right;   }
   static color get_color(const_node_ptr n)           {  return n->color_;    }
   static void set_color(node_ptr n, color c)         {  n->color_ = c;       }
   static color black()                               {  return color(0);     }
   static color red()                                 {  return color(1);     }
};

#include <boost/intrusive/link_mode.hpp>
namespace bi = boost::intrusive;

struct my_value_traits
{
   typedef my_rbtree_node_traits        node_traits;
   typedef node_traits::node            value_type;
   typedef node_traits::node_ptr        node_ptr;
   typedef node_traits::const_node_ptr  const_node_ptr;
   typedef value_type*                  pointer;
   typedef value_type const*            const_pointer;

   static const bi::link_mode_type link_mode = bi::link_mode_type::normal_link;

   static node_ptr       to_node_ptr    (value_type &value)       { return &value; } 
   static const_node_ptr to_node_ptr    (const value_type &value) { return &value; } 
   static pointer        to_value_ptr   (node_ptr n)              { return n;      } 
   static const_pointer  to_value_ptr   (const_node_ptr n)        { return n;      } 
};

#include <boost/intrusive/rbtree.hpp>
using mytree = bi::rbtree<my_node, bi::value_traits<my_value_traits> >;

#include <iostream>
#include <vector>

int main() {
    std::vector<my_node> storage { {1}, {3}, {4}, {2}, {3}, };

    mytree container;
    container.insert_equal(storage.begin(), storage.end());

    // NOW for the "have your cake and eat it too" moment:
    for (my_node& n : container) {
        std::cout << n.int_ 
            << " (parent: " << n.parent_ << ")"
            << " (left:   " << n.left_ << ")"
            << " (right:  " << n.right_ << ")"
            << "\n";
    }
}

Boost.Intrusive树的结构在bstree_算法()的文档中进行了解释。还解释了“标题”节点:

“在树的顶部专门使用一个节点。此节点的父指针指向树的根。其左指针指向树中最左边的节点,右指针指向最右边的节点。此节点用于表示结束迭代器。”

因此,您可以使用以下方式访问根节点:

root = rbtree_algorithms::get_parent(header);
如果您正在使用值特征构建自己的容器,正如sehe所解释的,因为提交:

基于树的容器有一个root()函数,该函数以O(1)的复杂度将迭代器返回到根节点(如果不存在,则返回end()),这可能更易于使用:

#include <boost/intrusive/set.hpp>
#include <cassert>

using namespace boost::intrusive;

struct MyClass : public set_base_hook<>
{
   friend bool operator<(const MyClass&, const MyClass&)
   {  return true;   }
};

int main()
{
   set<MyClass> set;
   //end() is returned when the tree is empty
   assert(set.root()  == set.end() );

   //insert myobject, must be root
   MyClass myobject;
   set.insert(myobject);
   assert(&*set.root() == &myobject);

   //erase and check root is again end()
   set.erase(set.root());
   assert(set.croot() == set.cend());

   return 0;   
}
#包括
#包括
使用名称空间boost::intrusive;
struct MyClass:public set\u base\u hook
{

friend bool运算符“Iv实现了红黑树”//您可能应该共享代码好吧,我的代码与示例中的代码一样。我只是在其中添加了一些详细信息。我的问题是,我不知道标题是否有指向根的链接,或者我应该指定它?您能更清楚地说明您的答案中添加了哪些不在我的答案中的内容吗?我想您也漏掉了一些单词(什么提交?)感谢您的评论。我试图进一步解释根节点是什么(第一个问题),并补充说,最近的提交允许直接从入侵容器中获取根节点(第二个问题的替代方案)以及该操作的O(1)复杂性(第三个问题).我已经编辑了答案,以包含缺少的单词和链接。谢谢。这是一个有价值的补充!
#include <boost/intrusive/set.hpp>
#include <cassert>

using namespace boost::intrusive;

struct MyClass : public set_base_hook<>
{
   friend bool operator<(const MyClass&, const MyClass&)
   {  return true;   }
};

int main()
{
   set<MyClass> set;
   //end() is returned when the tree is empty
   assert(set.root()  == set.end() );

   //insert myobject, must be root
   MyClass myobject;
   set.insert(myobject);
   assert(&*set.root() == &myobject);

   //erase and check root is again end()
   set.erase(set.root());
   assert(set.croot() == set.cend());

   return 0;   
}