二叉线索树
来源:互联网 发布:911色主站新域名 编辑:程序博客网 时间:2024/05/16 08:40
对于普通二叉树, 对于最底部的结点和只有一个孩子的结点, 我们通常将其没有元素的左右指针指向NULL. 对于线索树, 简而言之就是将这些NULL指针再次利用, 对于空闲的左指针, 将其指向该结点的前驱结点, 反之, 对于空闲的右指针, 将其指向该节点的后驱结点, 完成线索后的二叉树看上去是这样的
上图是一个中序二叉线索树, 直线是原始的二叉树指针, 曲线则是我们添加的线索.
对于线索二叉树的每个结点, 包含以下五项. 除了常规的三项, 还有ltag和rtag, ltag标记左边指针是二叉树指针还是一根线索, 同样rtag标记右指针.
struct Node{ int data; bool ltag, rtag;//0指向孩子, 1为前后趋线索 Node *left, *right;};
既然名字叫二叉线索树, 问题显然在于线索和构建线索, 假如要实现中序的线索, 在一次中序遍历中就能搞定, 下面看看代码的实现, 不过在众多的树中, 没有发现加个线索能带来多大的优点.
#include <iostream>using namespace std;struct Node{ int data; bool ltag, rtag;//0指向孩子, 1为前后趋线索 Node *left, *right;};Node *insert(Node *root, int key){ if (root == NULL) { root = new Node(); root->data = key; root->ltag = 1; root->rtag = 1; root->left = NULL; root->right = NULL; } else if (key >= root->data) { root->right = insert(root->right, key); root->rtag = 0; } else { root->left = insert(root->left, key); root->ltag = 0; } return root;}void in_order_traverse(Node *root){ if (root) { in_order_traverse(root->left); cout << "[" << root->ltag << "," <<root->data << "," << root->rtag << "]" << endl; in_order_traverse(root->right); }}void in_order_threading(Node *root, Node *pre, Node *next){ cout << "pos:" << root->data << " "; cout << "pre:"; if (pre == NULL) cout << "NULL "; else cout << pre->data << " "; cout << "next:"; if (next == NULL) cout << "NULL " << endl; else cout << next->data << " " << endl; if (root->left)//左子树的后继节点一定是当前作为跟的节点 in_order_threading(root->left, pre, root); else { root->left = pre; cout << "\t\t\tset:" << root->data << "'s L as:"; if (pre) cout << pre->data << endl; else cout << "NULL" << endl; } if (root->right)//右子树的前驱一定是当前作为跟的节点 in_order_threading(root->right, root, next); else { root->right = next; cout << "\t\t\tset:" << root->data << "'s R as:"; if (next) cout << next->data << endl; else cout << "NULL" << endl; }}Node *find(Node *root, int key){ if (!root) return NULL; if (root->data == key) return root; else if (key > root->data) return find(root->right, key); else return find(root->left, key);}int main(int argc, char const *argv[]){ int n = 10; int num[1000] = {4,5,1,2,7,6,9,8,0,3}; Node *root = NULL; for (int i = 0; i < n; i++) root = insert(root, num[i]); in_order_traverse(root); cout << endl; in_order_threading(root, NULL, NULL); Node *res = find(root, 6); if (res) { cout << res->left->data << endl; cout << res->data << endl; cout << res->right->data << endl; } return 0;}
看看运行效果, 从下可以清楚的看到递归的执行过程.与上图比较, 一点不差
为了输出执行过程, 在线索化函数中加了很多输出的代码, 将其全部都删除后代码可以更加简短
void in_order_threading(Node *root, Node *pre, Node *next){ if (root->left)//左子树的后继节点一定是当前作为跟的节点 in_order_threading(root->left, pre, root); else root->left = pre; if (root->right)//右子树的前驱一定是当前作为跟的节点 in_order_threading(root->right, root, next); else root->right = next;}
0 0
- 线索二叉树 --->树
- 线索二叉树算法
- C#线索二叉树
- 线索二叉树
- C#线索二叉树
- 线索二叉树
- 线索二叉树
- 线索化二叉树
- 线索二叉树
- C#线索二叉树
- C#线索二叉树
- 线索二叉树
- 线索二叉树实例
- 线索二叉树
- 线索二叉树算法
- C++线索二叉树
- 线索二叉树
- 线索二叉树实现
- COGS896圈奶牛
- Win7+VS2013+OpenCV3.0.0详细配置
- LeetCode题解:Odd Even Linked List
- Ubuntu里面的安装命令总结
- 编写demo,验证swith语句的表达式可以是enum类型
- 二叉线索树
- koala 编译scss不支持中文(包括中文注释),解决方案如下
- 枚举的详细举例解释
- 2012年及之后的ImageNet比赛的冠军、亚军和季军ImageNet winners after 2012
- poj1005--小学图形题
- 屏幕适配
- HDU 5627 Clarke and MST &高位枚举+并查集
- jQuery-源码阅读,pushStack()入栈方法
- 《leetCode》:Populating Next Right Pointers in Each Node