码迷,mamicode.com
首页 > 其他好文 > 详细

线索二叉树

时间:2014-07-19 14:32:38      阅读:215      评论:0      收藏:0      [点我收藏+]

标签:style   blog   color   os   数据   re   

数据定义:

 1 /*
 2  * 枚举类型定义     NO -> 没有线索化    YES -> 线索化了的
 3  */
 4 enum Thread { NO, YES }
 5 
 6 /*
 7  * 线索二叉树的结点类型定义
 8  */
 9 struct Node
10 {
11     ElementType data;                   // 数据域
12     Thread leftTag;                     // 左指针标志域
13     Thread rightTag;                    // 右指针标志域
14     struct Node *leftChild;             // 左指针域
15     struct Node *rightChild;            // 右指针域
16 };

为二叉树加序:

 1 /*
 2  * 为二叉树加前序线索   递归实现
 3  */
 4 void PreorderThread(Node *root)
 5 {
 6     static Node *prev = NULL;                               /* 指向当前结点的后序前件,用以记忆刚访问过的结点 */
 7     if(root != NULL) {                                      // 若二叉树为空,结束递归
 8         if(prev != NULL && prev->rightTag = YES)            // 若当前结点的前序前件需要加线索
 9             prev->rightChild = root;                        // 对当前结点的前序前件加指向后件(当前结点)的线索
10         if(root->leftChild == NULL) {                       // 若当前结点的左指针为空
11             root->leftTag = YES;                            // 将其修改为指向前件的线索
12             root->leftChild = prev; 
13         }   
14         if(root->rightChild == NULL)                        // 若当前结点的右指针域为空,修改右指针标志
15             root->rightTag = YES;   
16         prev = root;                                        // 将当前结点置为前件,后件将成为当前结点
17     
18         PreorderThread(root->leftChild);                    // 递归对左子树加前序线索
19         PreorderThread(root->rightChild);                   // 递归对右子树加前序线索
20     }
21 }
22 
23 /*
24  * 为二叉树加中序线索   递归实现
25  */
26 void InorderThread(Node *root)
27 {
28     static Node *prev = NULL;                               /* 指向当前结点的后序前件,用以记忆刚访问过的结点 */
29     if(root != NULL) {                                      // 若二叉树为空,结束递归
30         InorderThread(root->leftChild);                     /* 递归对左子树加中序线索 */
31     
32         if(prev != NULL && root->rightTag == YES)           // 若当前结点的中序前件需要加线索
33             prev->rightChild = root;                        // 对当前结点的中序前件加指向后件(当前结点)的线索
34         if(root->leftChild == NULL) {                       // 若当前结点的左指针为空
35             root->leftTag = YES;                            // 将其修改为指向前件的线索
36             root->leftChild = prev;     
37         }
38         if(root->rightChild == NULL)                        // 若当前结点的右指针域为空,修改右指针标志
39             root->rightTag = YES;
40         prev = root;                                        // 将当前结点置为前件,后件将成为当前结点
41 
42         InorderThread(root->rightChild);                    /* 递归对右子树加中序线索 */
43     }
44 }
45 
46 /*
47  * 为二叉树加后序线索   递归实现 */
48 void PostorderThread(Node *root)
49 {    
50     static Node *prev = NULL;                               /* 指向当前结点的后序前件,用以记忆刚访问过的结点 */
51     if(root != NULL) {                                      // 若二叉树为空,结束递归
52         PostorderThread(root->leftChild);                   // 递归对左子树后序线索化
53         PostorderThread(root->rightChild);                  // 递归对右子树后序线索化
54 
55         if(prev != NULL && root->rightTag == YES)           // 若当前结点的后序前件需要加线索
56             prev->rightChild = root;                        // 对当前结点的后序前件加指向后件(当前结点)的线索
57         if(rot->leftChild == NULL) {                        // 若当前结点的左指针为空
58             root->leftTag = YES;                            // 将其修改为指向前件的线索
59             root->rightChild = prev;
60         }
61         if(root->rightChild == NULL)                        // 若当前结点的右指针域为空,修改右指针标志
62             root->rightTag = YES;
63         prev = root;                                        // 将当前结点置为前件,后件将成为当前结点
64     }
65 }

利用加序的二叉树遍历:

 1 /*
 2  * 利用   前序线索树   遍历二叉树
 3  */
 4 void preorderThreadTreeTraversal(Node *root)
 5 {
 6     Node *currentNode = root;
 7     if(currentNode != NULL) {
 8         while(currentNode != NULL) {
 9             cout << currentNode->data;
10             if(currentNode->leftTag == NO)                      // 当前结点有左孩子,则使其左孩子变为当前结点
11                 currentNode = currentNode->leftChild;
12             else                                                // 若当前结点没有左孩子,则currentNode指向当前结点的前序后件
13                 currentNode = currentNode->rightChild;
14         }
15     }
16 }
17 
18 /*
19  * 利用   中序线索树   遍历二叉树
20  */
21 void inorderThreadTreeTraversal(Node *root)
22 {
23     Node *currentNode = root;                                   // 设定currentNode初始指向中序线索二叉树的根结点
24     if(currentNode != NULL) {                                   // 二叉树为空,结束遍历
25         while(currentNode->leftTag == NO)                       // 找到中序遍历的第一个结点
26             currentNode = currentNode->leftChild;
27         do {                                                    /* 依次找出每个结点的后件,直到输出中序线索二叉树的最右边一个结点 */
28             cout << currentNode->data;                           /* 输出当前结点数据 */
29             if(currentNode->rightTag == YES)                    // 若当前结点的右指针是线索,其指示为中序后件
30                 currentNode = currentNode->rightNode;
31             else {                                              /* 若当前结点的右指针指向右孩子 */
32                 currentNode = currentNode->rightChild;          // 从右孩子结点出发找中序后件
33                 while(currentNode->leftTag == NO)               // 找到右子树的最左边一个结点,即为中序后件
34                     currentNode = currentNode->leftChild;
35             }
36         } while(currentNode != NULL); 
37     }
38 }
39 
40 /*
41  * 利用   后序线索树   遍历二叉树
42  */
43 void postorderThreadTreeTraversal( Node *root)
44 {
45     
46 }

 

OK哒!O(∩_∩)O哈哈~

线索二叉树,布布扣,bubuko.com

线索二叉树

标签:style   blog   color   os   数据   re   

原文地址:http://www.cnblogs.com/gotodsp/p/3854486.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!