关于真二叉树用前序和后序还原

二叉树已知前序和中序求后序或者二叉树已知中序和后序求前序已经烂大街了,所以写一下这篇博客

真二叉树:任何一个父节点只要有孩子就必定有左孩子和右孩子

前序遍历 : 根--左--右

后序遍历:左--右--根

当知道前序遍历和后序

从最底层孩子节点看起,规律为     前右=后右 右为同级右兄弟节点   前左=后右 左为父亲节点,然后将这两个规律循环就可还原此真二叉树代码如下


//目的 实现已知前序和后序的真二叉树还原并求出中序
//思路:前序和后序获得二叉树最底层的左右孩子节点依次往上还原至根从而得到原真二叉树 

#include "stdio.h"
#include"stdlib.h"
typedef struct List{
    int a;
    struct List* next;
    struct List* last;
    struct List* left_child;
    struct List* right_child;
    struct List* left_b;
    struct List* right_b;    
} List;

typedef struct List_T_B{
    struct List* top;
    struct List* bottom;
}List_T_B;
//初始化List链表 
List_T_B* init_list(){
    List* top=(List*)malloc(sizeof(List));
    List* bottom=(List*)malloc(sizeof(List));
    top->a=0;
    top->next=bottom;
    top->last=NULL;
    top->left_b=NULL;
    top->left_child=NULL;
    top->right_b=NULL;
    top->right_child=NULL;
    bottom->a=0;
    bottom->next=NULL;
    bottom->last=top;
    bottom->left_b=NULL;
    bottom->left_child=NULL;
    bottom->right_b=NULL;
    bottom->right_child=NULL;
    List_T_B* list_st=(List_T_B*)malloc(sizeof(List_T_B));
    list_st->top=top;
    list_st->bottom=bottom;
    return list_st;
}
//插入链表 
void insert_list(List* top,int number){
    List* Create_List=(List*)malloc(sizeof(List));
    Create_List->a=number;
    Create_List->left_b=NULL;
    Create_List->left_child=NULL;
    Create_List->right_b=NULL;
    Create_List->right_child=NULL;
    List* next=top;
    while(next->next->next!=NULL){
        next=next->next;
    }
    Create_List->next=next->next;
    Create_List->last=next;
    next->next->last=Create_List;
    next->next=Create_List;
}
//确定兄弟节点 
void makesure_b(List_T_B* first,List_T_B* bottom){
    //printf("进入68行\n");
    List* next_1=first->top;
    while(next_1->next->next!=NULL){
        next_1=next_1->next;
        List* next_2=bottom->top;
        while(next_2->next->next->next!=NULL){
            if(next_1->a==next_2->a&&next_1->next->a==next_2->next->a){
                next_1->right_b=next_1->next;
                next_1->next=next_1->next->next;
                next_1->next->last=next_1;
                next_2->right_b=next_2->next;
                next_2->next=next_2->next->next;
                next_2->next->last=next_2;
                break;
            }
            next_2=next_2->next;
        //    printf("%d\n",next_2->a);
        }
    //    printf("\n");
    }
}
//确定父节点
void makesure_father(List_T_B* one,List_T_B* two){
    //printf("进入87行\n");
    List* next_1=one->bottom;
    while(next_1->last->last->last!=NULL){
        if(one->top->next->next->next==NULL){
            break;
        }
        List* next_2=two->top;
        next_1=next_1->last;
        while(next_2->next->next!=NULL){
            if(next_1->a==next_2->a&&next_1->last->a==next_2->next->a){
                next_1->last->left_child=next_1;
                next_1->last->right_child=next_1->right_b;
                next_1->next->last=next_1->last;
                next_1->last->next=next_1->next;
                next_2->next->left_child=next_2;
                next_2->next->right_child=next_2->right_b;
                next_2->last->next=next_2->next;
                next_2->next->last=next_2->last;
                break;
            }
            next_2=next_2->next;
        }
    }
} 
void print_list(List* one,List* two){
    List* next=one;
    while(next->next->next!=NULL){
        printf("%d",next->next->a);
        next=next->next;
    }
    next=two;
    while(next->next->next!=NULL){
        printf("%d",next->next->a);
        next=next->next;
    }
} 
//中序遍历此树
void print_tree(List* one){
    if(one->left_child!=NULL){
        print_tree(one->left_child);
    }
    printf("%d   ",one->a);
    if(one->right_child!=NULL){
        print_tree(one->right_child);
    }
    
} 
int main(){
    //储存先序遍历链表  
    List_T_B* one=init_list();
    //储存后序遍历链表 
    List_T_B* two=init_list();
    int len,len_1;
    int sum;
    printf("请输入列表长度");
    scanf("%d",&len);
    printf("请输入先序列表\n");
    len_1=len;
    while(len>0){
        scanf("%d",&sum);
        insert_list(one->top,sum);
        len--;
    }
    printf("请输入后序列表\n");
    while(len_1>0){
        scanf("%d",&sum);
        insert_list(two->top,sum);
        len_1--;
    }
    while(one->top->next->next->next!=NULL){
        makesure_b(one,two);
        makesure_father(one,two);
    //    print_list(one->top,two->top);
        //system("pause");
    }
    printf("输出中序遍历");
    print_tree(one->top->next);
    return 0;
}
/*
   作者:吾非善类  
*/

 

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值