免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 2375 | 回复: 6
打印 上一主题 下一主题

[数据结构] 对priority search tree的疑惑 [复制链接]

论坛徽章:
16
2015亚冠之吉达阿赫利
日期:2015-08-17 11:21:462015年迎新春徽章
日期:2015-03-04 09:58:11酉鸡
日期:2014-12-07 09:06:19水瓶座
日期:2014-11-04 14:23:29天秤座
日期:2014-03-02 08:57:52双鱼座
日期:2014-02-22 13:07:56午马
日期:2014-02-14 11:08:18双鱼座
日期:2014-02-13 11:09:37卯兔
日期:2014-02-06 15:10:34子鼠
日期:2014-01-20 14:48:19戌狗
日期:2013-12-19 09:37:46射手座
日期:2013-12-19 09:33:47
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2012-05-13 19:38 |只看该作者 |倒序浏览
30可用积分
本帖最后由 embeddedlwp 于 2012-05-13 19:40 编辑

prio_tree_remove函数中,最后会调用prio_tree_replace函数对节点进行替换
  1. 143struct prio_tree_node *prio_tree_replace(struct prio_tree_root *root,
  2. 144                struct prio_tree_node *old, struct prio_tree_node *node)
  3. 145{
  4. 146        INIT_PRIO_TREE_NODE(node);
  5. 147
  6. 148        if (prio_tree_root(old)) {
  7. 149                BUG_ON(root->prio_tree_node != old);
  8. 150                /*
  9. 151                 * We can reduce root->index_bits here. However, it is complex
  10. 152                 * and does not help much to improve performance (IMO).
  11. 153                 */
  12. 154                node->parent = node;
  13. 155                root->prio_tree_node = node;
  14. 156        } else {
  15. 157                node->parent = old->parent;
  16. 158                if (old->parent->left == old)
  17. 159                        old->parent->left = node;
  18. 160                else
  19. 161                        old->parent->right = node;
  20. 162        }
  21. 163
  22. 164        if (!prio_tree_left_empty(old)) {
  23. 165                node->left = old->left;
  24. 166                old->left->parent = node;
  25. 167        }
  26. 168
  27. 169        if (!prio_tree_right_empty(old)) {
  28. 170                node->right = old->right;
  29. 171                old->righ人t->parent = node;
  30. 172        }
  31. 173
  32. 174        return old;
  33. 175}
复制代码
以cluter兄画的这个图为例,


prio_tree_replace函数会执行两次:

一:

4,3,7 ->left = 4,2,6
4,2,6->parent=4,3,7
=============
4,2,6->left=4,2,6
4,2,6->parent=4,2,6
=============
4,2,6->right=5,1,6
5,1,6->parent=4,2,6

二:

0,7,7->right=5,2,7
5,2,7->parent=0,7,7
============
5,2,7->left=5,2,7
5,2,7->parent=5,2,7
============
5,2,7->right=6,1,7
6,1,7->parent=5,2,7

从置换的结果来看,5,2,7的parent指针指向了自己,5,2,7的left指针指向了自己,而不是4,2,6,是我什么地方理解错了吗?

论坛徽章:
0
2 [报告]
发表于 2012-05-14 09:13 |只看该作者
这里没有循环语句。怎么来的循环?
还有,如果删除掉一个节点,就需要一次替换就可以。
后面的替换者及以后的相互指针关系是保留下来的。没有变化。

论坛徽章:
16
2015亚冠之吉达阿赫利
日期:2015-08-17 11:21:462015年迎新春徽章
日期:2015-03-04 09:58:11酉鸡
日期:2014-12-07 09:06:19水瓶座
日期:2014-11-04 14:23:29天秤座
日期:2014-03-02 08:57:52双鱼座
日期:2014-02-22 13:07:56午马
日期:2014-02-14 11:08:18双鱼座
日期:2014-02-13 11:09:37卯兔
日期:2014-02-06 15:10:34子鼠
日期:2014-01-20 14:48:19戌狗
日期:2013-12-19 09:37:46射手座
日期:2013-12-19 09:33:47
3 [报告]
发表于 2012-05-14 20:43 |只看该作者
回复 2# wangzhen11aaa

看prio_tree_remove函数的实现:
  1. 264void prio_tree_remove(struct prio_tree_root *root, struct prio_tree_node *node)
  2. 265{
  3. 266        struct prio_tree_node *cur;
  4. 267        unsigned long r_index, h_index_right, h_index_left;
  5. 268
  6. 269        cur = node;
  7. 270
  8. 271        while (!prio_tree_left_empty(cur) || !prio_tree_right_empty(cur)) {
  9. 272                if (!prio_tree_left_empty(cur))
  10. 273                        get_index(root, cur->left, &r_index, &h_index_left);
  11. 274                else {
  12. 275                        cur = cur->right;
  13. 276                        continue;
  14. 277                }
  15. 278
  16. 279                if (!prio_tree_right_empty(cur))
  17. 280                        get_index(root, cur->right, &r_index, &h_index_right);
  18. 281                else {
  19. 282                        cur = cur->left;
  20. 283                        continue;
  21. 284                }
  22. 285
  23. 286                /* both h_index_left and h_index_right cannot be 0 */
  24. 287                if (h_index_left >= h_index_right)
  25. 288                        cur = cur->left;
  26. 289                else
  27. 290                        cur = cur->right;
  28. 291        }
  29. 292
  30. 293        if (prio_tree_root(cur)) {
  31. 294                BUG_ON(root->prio_tree_node != cur);
  32. 295                __INIT_PRIO_TREE_ROOT(root, root->raw);
  33. 296                return
  34. 297        }
  35. 298
  36. 299        if (cur->parent->right == cur)
  37. 300                cur->parent->right = cur->parent;
  38. 301        else
  39. 302                cur->parent->left = cur->parent;
  40. 303
  41. 304        while (cur != node)
  42. 305                cur = prio_tree_replace(root, cur->parent, cur);
  43. 306}
复制代码
最后是有一个循环的。

从cluter兄的那个例子来看,这里需要置换两次,把真实节点带入代码中,如上面我的分析,“5,2,7的parent指针指向了自己,5,2,7的left指针指向了自己,而不是4,2,6,”
这样5,2,7的parent,left都指错了位置,请指教~!

   

论坛徽章:
16
2015亚冠之吉达阿赫利
日期:2015-08-17 11:21:462015年迎新春徽章
日期:2015-03-04 09:58:11酉鸡
日期:2014-12-07 09:06:19水瓶座
日期:2014-11-04 14:23:29天秤座
日期:2014-03-02 08:57:52双鱼座
日期:2014-02-22 13:07:56午马
日期:2014-02-14 11:08:18双鱼座
日期:2014-02-13 11:09:37卯兔
日期:2014-02-06 15:10:34子鼠
日期:2014-01-20 14:48:19戌狗
日期:2013-12-19 09:37:46射手座
日期:2013-12-19 09:33:47
4 [报告]
发表于 2012-05-16 12:04 |只看该作者
顶起~!

论坛徽章:
16
2015亚冠之吉达阿赫利
日期:2015-08-17 11:21:462015年迎新春徽章
日期:2015-03-04 09:58:11酉鸡
日期:2014-12-07 09:06:19水瓶座
日期:2014-11-04 14:23:29天秤座
日期:2014-03-02 08:57:52双鱼座
日期:2014-02-22 13:07:56午马
日期:2014-02-14 11:08:18双鱼座
日期:2014-02-13 11:09:37卯兔
日期:2014-02-06 15:10:34子鼠
日期:2014-01-20 14:48:19戌狗
日期:2013-12-19 09:37:46射手座
日期:2013-12-19 09:33:47
5 [报告]
发表于 2012-05-19 13:24 |只看该作者
顶起!

论坛徽章:
16
2015亚冠之吉达阿赫利
日期:2015-08-17 11:21:462015年迎新春徽章
日期:2015-03-04 09:58:11酉鸡
日期:2014-12-07 09:06:19水瓶座
日期:2014-11-04 14:23:29天秤座
日期:2014-03-02 08:57:52双鱼座
日期:2014-02-22 13:07:56午马
日期:2014-02-14 11:08:18双鱼座
日期:2014-02-13 11:09:37卯兔
日期:2014-02-06 15:10:34子鼠
日期:2014-01-20 14:48:19戌狗
日期:2013-12-19 09:37:46射手座
日期:2013-12-19 09:33:47
6 [报告]
发表于 2012-05-21 08:55 |只看该作者
顶起!

论坛徽章:
16
2015亚冠之吉达阿赫利
日期:2015-08-17 11:21:462015年迎新春徽章
日期:2015-03-04 09:58:11酉鸡
日期:2014-12-07 09:06:19水瓶座
日期:2014-11-04 14:23:29天秤座
日期:2014-03-02 08:57:52双鱼座
日期:2014-02-22 13:07:56午马
日期:2014-02-14 11:08:18双鱼座
日期:2014-02-13 11:09:37卯兔
日期:2014-02-06 15:10:34子鼠
日期:2014-01-20 14:48:19戌狗
日期:2013-12-19 09:37:46射手座
日期:2013-12-19 09:33:47
7 [报告]
发表于 2012-05-23 22:35 |只看该作者
顶起!
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP