后序线索二叉树

 1 #include<iostream>
 2 #include<cstring>
 3 #include<cstdio>
 4 #include<algorithm>
 5
 6 using namespace std;
 7
 8 struct TREE{
 9     int    val;
10     TREE *ch[2];
11     TREE *thread;//该节点的线索的下一个节点
12     TREE(){}
13     TREE(int val){
14         this->val = val;
15         ch[0] = ch[1] = NULL;
16         thread = NULL;
17     }
18 };
19
20 void buildT(TREE * &T){
21     int x;
22     scanf("%d", &x);
23     if(x == -1) return ;
24
25     T = new TREE(x);
26     buildT(T->ch[0]);
27     buildT(T->ch[1]);
28 }
29
30
31 void postThread(TREE *T, TREE *pre){//感觉后序线索二叉树的思路和中序及前序的思路完全不一样啊
32     if(!T) return;
33     postThread(T->ch[0], T);
34     postThread(T->ch[1], T);
35     if(pre){
36         if(pre->ch[0] == T && pre->ch[1])//T是左子树
37             T->thread = pre->ch[1]; //T的下一个节点就是它的兄弟节点
38         else //T是右子树
39             T->thread = pre;//T的下一个节点就是它 的父亲节点
40     }
41 }
42
43 void printT_pre(TREE *T){//前序打印
44     if(!T) return ;
45     printf("%d ", T->val);
46     printT_pre(T->ch[0]);
47     printT_pre(T->ch[1]);
48 }
49
50 void printT_Thread(TREE *T){//后序线索打印
51     TREE *root = T;
52     bool flag = true;//表明T所在的字数没有访问过
53     while(1){
54         while(flag && T->ch[0]) T = T->ch[0];
55         printf("%d ", T->val);
56         if(T->thread->ch[0] == T || T->thread->ch[1] == T)
57             flag = false;//如果 T没有兄弟节点了,就一直沿着它的父节点向上走
58         else flag = true;
59         T = T->thread;
60         if(T == root){//再次回到最顶端父节点时, 结束!
61            printf("%d ", T->val);
62            break;
63         }
64     }
65 }
66
67 int main(){
68     TREE *T = NULL;
69     buildT(T);
70     printT_pre(T);
71     printf("\n");
72     postThread(T, NULL);
73     printT_Thread(T);
74     printf("\n");
75     return 0;
76 } 
时间: 2024-09-27 17:45:22

后序线索二叉树的相关文章

[三叉链表]利用三叉链表找后序线索二叉树的后继

//Three.h #ifndef THREE_H #define THREE_H #include <iostream> #include <string.h> using namespace std; typedef enum{Link, Thread} Tag; typedef struct ThreeNode { char data; struct ThreeNode *lChild, *rChild, *Parent;//采用三叉链表,增加一个指向双亲的结点 Tag lT

二叉树的前序、中序和后序线索化

二叉树是一种非线性结构,遍历二叉树需要通过递归或者用栈辅助实现非递归的遍历. 用二叉树作为压缩存储结构时,取到一个结点,只能获取节点的左孩子和右孩子,不能直接得到结点的任一遍历序列的前驱或者后继.为了实现这种遍历,偶们利用二叉树中指向左右子树的空指针来存放结点的前驱和后继. 线索化二叉树思路: 当某一结点的左结点或结右点存在NULL时,则该结点的为空的子结点需要线索化. 在进行线索化时,结点的前驱指向前一个访问过的结点,故定义一个指针prev来保存前一个结点:结点的后继偶们并不知道,则对于未来的

数据结构:中序线索二叉树

//所谓线索二叉树无非是为了让原本指向NULL的节点指向一个详细的 //已经存在的节点,逻辑上实现指针的无空指向的实现.以下是我中 //序线索二叉树的实现.还是把先序线索二叉树与后序线索分开来写吧. #include<iostream> using namespace std; template<typename Type> struct Node { Type data; bool rflags;//false为线. bool lflags; Node<Type> *

【数据结构】 非递归前中后序遍历二叉树

数据结构学的递归了,深入了解后写一个三序非递归的版本. //测试数据:abd##eg##h##c#f## #include <cstdio> #include <iostream> typedef char ElemType; typedef struct Node { ElemType elem; struct Node *lchild,*rchild; }Node,*BiTree; typedef struct{ BiTree *base; BiTree *top; int s

【TOJ 1224】数据结构练习题――后序遍历二叉树

Description 给定一颗二叉树,要求输出二叉树的深度以及后序遍历二叉树得到的序列.本题假设二叉树的结点数不超过1000. Input 输入数据分为多组,第一行是测试数据的组数n,下面的n行分别代表一棵二叉树.每棵二叉树的结点均为正整数,数据为0代表当前结点为空,数据为-1代表二叉树数据输入结束,-1不作处理.二叉树的构造按照层次顺序(即第1层1个整数,第2层2个,第3层4个,第4层有8个......,如果某个结点不存在以0代替). Output 输出每棵二叉树的深度以及后序遍历二叉树得到

中序线索二叉树

虽说对于二叉树的遍历操作来说非递归法使用用户自定义的栈来代替递归使用时的系统栈,可以得到不小的效率提升,但将二叉树线索化时能将用户栈也省略掉进一步提高了效率. 对于二叉树的链表结构,n个结点的二叉树有n+1个空链域(每个叶节点都有两个空链域),而线索二叉树就把这些空链域有效的利用了起来,在一般的二叉树中,我们只知道每个结点的左右孩子,并不知道某个结点在某种遍历方式下的直接前驱和直接后继,如果能够知道前驱和后继信息,就可以把二叉树看作一个链表结构,从而可以像遍历链表那样来遍历二叉树,进而提高效率.

中序线索二叉树创建及其遍历

通过考察各种二叉链表,不管儿叉树的形态如何,空链域的个数总是多过非空链域的个数.准确的说,n各结点的二叉链表共有2n个链域,非空链域为n-1个,但其中的空链域却有n+1个.如下图所示. 因此,提出了一种方法,利用原来的空链域存放指针,指向树中其他结点.这种指针称为线索. 记ptr指向二叉链表中的一个结点,以下是建立线索的规则: (1)如果ptr->lchild为空,则存放指向中序遍历序列中该结点的前驱结点.这个结点称为ptr的中序前驱: (2)如果ptr->rchild为空,则存放指向中序遍历

(树)根据中序后序构建二叉树

题目:根据中序和后序遍历构建二叉树 思路:利用递归加上分治的思想.先找到根节点的值,然后在根据中序遍历找到根节点的左右两边的值,然后在递归的处理左右两边的左右子树.这里的关键在于怎么处理递归的左右子树的范围,代码里面详细解释 代码: class Solution { public: TreeNode *buildTree(vector<int> &inorder, vector<int> &postorder) { vector<int>::size_t

非递归 后序遍历二叉树

方法有很多,这里只举一种,先定义栈结点的数据结构typedef struct{Node * p; int rvisited;}SNode //Node 是二叉树的结点结构,rvisited==1代表p所指向的结点的右结点已被访问过. lastOrderTraverse(BiTree bt){ //首先,从根节点开始,往左下方走,一直走到头,将路径上的每一个结点入栈. p = bt; while(bt){ push(bt, 0); //push到栈中两个信息,一是结点指针,一是其右结点是否被访问过