二叉树的基本操作(顺序二叉树)

该代码的二叉树结点是数字,采用的是用数组存储,一般使用在空结点较少的情况,使用的时候,一定要清楚二叉树元素在数组中的存储顺序特点,比如左右子树序号有什么特点,怎么由孩子结点的找到双亲节点……

#include<iostream>
#include<cmath>
#include<cstdlib>
using namespace std;

const int MAX_TREE_SIZE=100;
const int Nil=0;
typedef int TElemType;
typedef int SqBiTree[MAX_TREE_SIZE];

struct position{
    //按满二叉树计算
    int level,order;
};

//函数声明
void show();
void InitBiTree(SqBiTree T);
void DestroyBiTree(SqBiTree T);
void CreateBiTree(SqBiTree T);
int ClearBiTree(SqBiTree T);
bool EmptyBiTree(SqBiTree T);
int BiTreeDepth(SqBiTree T);
TElemType BiTreeRoot(SqBiTree T);
TElemType GetValue(SqBiTree T,position e);
bool Assign(SqBiTree T,position e,TElemType value);
TElemType Parent(SqBiTree T,TElemType e);
TElemType LeftChild(SqBiTree T,TElemType e);
TElemType RightChild(SqBiTree T,TElemType e);
TElemType LeftSibling(SqBiTree T,TElemType e);
TElemType RightSibling(SqBiTree T,TElemType e);
void InsertChild(SqBiTree T,TElemType p,int LR,SqBiTree c);
void Move(SqBiTree q,int j,SqBiTree T,int i);
void PreOrderTraverse(SqBiTree T,int i);
void InOrderTraverse(SqBiTree T,int i);
void PostOrderTraverse(SqBiTree T,int i);
void LevelOrderTraverse(SqBiTree T);
void Print(SqBiTree T);

int main(){
    int x,LR,action;
    position p;
    TElemType e;
    SqBiTree T,s;
    show();
    while(cin>>action){
        switch(action){
        case 1:
            system("cls");
            InitBiTree(T);
            cout<<"初始化二叉树成功"<<endl<<endl;
            break;
        case 2:
            system("cls");
            CreateBiTree(T);
            cout<<"二叉树创建成功"<<endl<<endl;
            break;
        case 3:
            system("cls");
            cout<<"先序遍历二叉树,结果为:"<<endl;
            PreOrderTraverse(T,0);
            cout<<endl<<endl;
            break;
        case 4:
            system("cls");
            cout<<"中序遍历二叉树,结果为:"<<endl;
            InOrderTraverse(T,0);
            cout<<endl<<endl;
            break;
        case 5:
            system("cls");
            cout<<"后序遍历二叉树,结果为:"<<endl;
            PostOrderTraverse(T,0);
            cout<<endl<<endl;
            break;
        case 6:
            system("cls");
            cout<<"层序遍历二叉树,结果为:"<<endl;
            LevelOrderTraverse(T);
            cout<<endl<<endl;
            break;
        case 7:
            system("cls");
            cout<<"请输入层数和序号:"<<endl;
            cin>>p.level>>p.order;
            cout<<"第"<<p.level<<"层"<<" 第"<<p.order<<"个结点的值为: "<<GetValue(T,p);
            cout<<endl<<endl;
            break;
        case 8:
            system("cls");
            ClearBiTree(T);
            cout<<"已清空二叉树"<<endl<<endl;
            break;
        case 9:
            InitBiTree(s);
            cout<<"请输入右子树为空的二叉树s:"<<endl;
            CreateBiTree(s);
            cout<<"待插入的二叉树已经建立,请输入将要插入的结点的值:"<<endl;
            cin>>e;
            cout<<"待插入的二叉树成为左孩子(0),右孩子(1):"<<endl;
            cin>>LR;
            InsertChild(T,e,LR,s);
            cout<<"操作成功"<<endl<<endl;
            break;
        case 10:
            system("cls");
            cout<<"二叉树的各结点为:"<<endl;
            Print(T);
            cout<<endl;
            break;
        case 11:
            system("cls");
            cout<<"请输入双亲结点"<<endl;
            cin>>e;
            cout<<"左孩子结点的值为: "<<LeftChild(T,e)<<endl;
            break;
        case 12:
            system("cls");
            cout<<"请输入双亲结点"<<endl;
            cin>>e;
            cout<<"右孩子结点的值为: "<<RightChild(T,e)<<endl;
            break;
        case 13:
            system("cls");
            cout<<"请输入右兄弟结点"<<endl;
            cin>>e;
            cout<<"左兄弟结点的值为: "<<LeftSibling(T,e)<<endl;
            break;
        case 14:
            system("cls");
            cout<<"请输入左兄弟结点"<<endl;
            cin>>e;
            cout<<"右兄弟结点的值为: "<<RightSibling(T,e)<<endl;
            break;
        case 15:
            system("cls");
            cout<<"请输入孩子结点"<<endl;
            cin>>e;
            cout<<"双亲结点的值为: "<<Parent(T,e)<<endl;
            break;
        case 16:
            system("cls");
            cout<<"二叉树的深度为: "<<BiTreeDepth(T)<<endl;
            break;
        case 17:
            system("cls");
            cout<<"根结点的值为: "<<BiTreeRoot(T)<<endl;
            break;
        case 18:
            system("cls");
            cout<<"请输入结点的层数和在该层的序号: "<<endl;
            cin>>p.level>>p.order;
            cout<<"请输入将赋给该结点的值:"<<endl;
            cin>>e;
            Assign(T,p,e);
            cout<<"赋值成功!"<<endl;
            break;
        }
        system("pause");
        system("cls");
        show();
    }

}
void show(){
    cout<<"+-----------------------------------------------+"<<endl;
    cout<<"|                                               |"<<endl;
    cout<<"|         1->初始化二叉树                       |"<<endl;
    cout<<"|         2->创建二叉树                         |"<<endl;
    cout<<"|         3->先序遍历二叉树                     |"<<endl;
    cout<<"|         4->中序遍历二叉树                     |"<<endl;
    cout<<"|         5->后序遍历二叉树                     |"<<endl;
    cout<<"|         6->层序遍历二叉树                     |"<<endl;
    cout<<"|         7->获取树结点的值                     |"<<endl;
    cout<<"|         8->清空二叉树                         |"<<endl;
    cout<<"|         9->插入二叉树                         |"<<endl;
    cout<<"|        10->打印二叉树                         |"<<endl;
    cout<<"|        11->获取左孩子                         |"<<endl;
    cout<<"|        12->获取右孩子                         |"<<endl;
    cout<<"|        13->获取左兄弟                         |"<<endl;
    cout<<"|        14->获取右兄弟                         |"<<endl;
    cout<<"|        15->获取结点双亲                       |"<<endl;
    cout<<"|        16->获取二叉树深度                     |"<<endl;
    cout<<"|        17->获取根节点                         |"<<endl;
    cout<<"|        18->给结点赋值                         |"<<endl;
    cout<<"+-----------------------------------------------+"<<endl;

}

void InitBiTree(SqBiTree T){
    int i;
    for(i=0;i<MAX_TREE_SIZE;i++){
        T[i]=Nil;//初始值为Nil
    }
}

void DestroyBiTree(SqBiTree T){
    int i;
    for(i=0;i<MAX_TREE_SIZE;i++){
        T[i]=Nil;//初始值为Nil
    }
}

void CreateBiTree(SqBiTree T){
    int i=0;
    cout<<"请按层需输入结点的值(数字),0表示空结点,以999结束,结点数<"<<MAX_TREE_SIZE<<":"<<endl;
    while(1){
        cin>>T[i];
        if(T[i]==999){
            T[i]=Nil;
            break;
        }
        i++;
    }
    for(i=1;i<MAX_TREE_SIZE;i++){
        if(i!=0 && T[(i+1)/2-1]==Nil && T[i]!=Nil){
            cout<<"出现无双亲的非根节点!"<<endl;
            break;
        }
    }
}

int ClearBiTree(SqBiTree T){
    int i;
    for(i=0;i<MAX_TREE_SIZE;i++){
        T[i]=Nil;//初始值为Nil
    }
}

//判断二叉树是否为空
bool EmptyBiTree(SqBiTree T){
    if(T[0]==Nil){
        return true;
    } else {
        return false;
    }
}

//获取二叉树的深度
int BiTreeDepth(SqBiTree T){
    int i=MAX_TREE_SIZE-1,j=0;
    while(i>=0){
        //从后往前寻找到第一个结点不是默认值的下标
        if(T[i]!=Nil){
            break;
        }
        i--;
    }
    while(i>=pow(2,j)){
        j++;
    }
    return j;
}

//获取根结点的值
TElemType BiTreeRoot(SqBiTree T){
    if(EmptyBiTree(T)){
        return Nil;
    } else {
        return T[0];
    }
}

//获取给定结点e的值
TElemType GetValue(SqBiTree T,position e){
    return T[int(pow(2,e.level-1)+e.order-2)];
}

//给结点赋值
bool Assign(SqBiTree T,position e,TElemType value){
    int i=pow(2,e.level-1)+e.order-2;
    if(value!=Nil && T[(i+1)/2-1]==Nil){
        cout<<"非法操作,禁止给不含双亲的孩子赋非空值"<<endl;
        return false;
    }
    else if(value==Nil && (T[i*2+1]!=Nil || T[i*2+2]!=Nil)){
        cout<<"非法操作,禁止给含有孩子的双亲赋空值"<<endl;
        return false;
    }
    T[i]=value;
    return true;
}

//获取双亲结点的值
TElemType Parent(SqBiTree T,TElemType e){
    if(!EmptyBiTree(T)){
        for(int i=0;i<=MAX_TREE_SIZE;i++){
            if(T[i]==e){//判断结点e是否存在与二叉树中
                return T[(i+1)/2-1];
            }
        }
    } else {
        return Nil;//二叉树为空或者没有结点e
    }
}

//获取左孩子的值
TElemType LeftChild(SqBiTree T,TElemType e){
    if(!EmptyBiTree(T)){
        for(int i=0;i<MAX_TREE_SIZE;i++){
            if(T[i]==e){//判断结点e是否存在与二叉树中
                return T[i*2+1];//返回其左孩子的值
            }
        }
    } else {
        return Nil;//二叉树为空或者没有结点e
    }
}

//获取右孩子的值
TElemType RightChild(SqBiTree T,TElemType e){
    if(!EmptyBiTree(T)){
        for(int i=0;i<MAX_TREE_SIZE;i++){
            if(T[i]==e){//判断结点e是否存在与二叉树中
                return T[i*2+2];//返回其左孩子的值
            }
        }
    } else {
        return Nil;//二叉树为空或者没有结点e
    }
}

//获取左兄弟的值
TElemType LeftSibling(SqBiTree T,TElemType e){
     if(!EmptyBiTree(T)){
        for(int i=0;i<MAX_TREE_SIZE;i++){
            if(T[i]==e && i%2==0){//判断结点e是否存在与二叉树中
                //并且存在有兄弟,i%2=0为右孩子
                return T[i-1];//返回其左兄弟的值
            }
        }
    } else {
        return Nil;//二叉树为空或者没有结点e
    }
}

//获取右兄弟的值
TElemType RightSibling(SqBiTree T,TElemType e){
     if(!EmptyBiTree(T)){
        for(int i=0;i<MAX_TREE_SIZE;i++){
            if(T[i]==e && i%2==1){//判断结点e是否存在与二叉树中
                //并且存在有兄弟,i%2==1为左孩子
                return T[i+1];//返回其右兄弟的值
            }
        }
    } else {
        return Nil;//二叉树为空或者没有右兄弟
    }
}
//仔细观察,寻找双亲、左右孩子和左右兄弟的方法都类似
//首先都得判断二叉树是否为空,然后再判断时候该结点是否存在
//最后根据判断返回结点值

//插入二叉树
void InsertChild(SqBiTree T,TElemType p,int LR,SqBiTree c){
    //非空二叉树c要插到T中的p结点下面,成为p结点的(左或右)子树
    //非空二叉树c与T无交集,且右子树为空,p结点原有的左或右子树成为s的右子树
    //LR=0 c成为左子树,LR=1 c成为右子树
    int i=0,j,k;
    //查找p结点的序号
    //int temp=int(pow(2,BiTreeDepth(T)));
    //for(j=0;j<temp-1;j++){
    //  if(T[j]==p){
    //      break;
    //  }
    //}
    //或者
    for(j=0;j<MAX_TREE_SIZE;j++){
        if(T[j]==p){
            break;
        }
    }
    k=2*j+1+LR;//k为c子树将要插入的序号
    if(T[k]!=Nil){
        Move(T,k,T,2*k+2);
    }
    Move(c,i,T,k);
}

//移动二叉树
void Move(SqBiTree q,int j,SqBiTree T,int i){
    //把从二叉树q的j结点开始的子树 移为 从二叉树T的i结点开始的子树
    if(q[2*j+1]!=Nil){//q的左子树不为空
        Move(q,(2*j+1),T,(2*i+1));
    }
    if(q[2*j+2]!=Nil){//q的右子树不为空
        Move(q,(2*j+2),T,(2*i+2));
    }
    T[i]=q[j];
    q[i]=Nil;
}

//先序遍历
void PreOrderTraverse(SqBiTree T,int i){
    cout<<T[i]<<‘ ‘;
    if(T[2*i+1]!=Nil){
        PreOrderTraverse(T,2*i+1);
    }
    if(T[2*i+2]!=Nil){
        PreOrderTraverse(T,2*i+2);
    }
}

//中序遍历
void InOrderTraverse(SqBiTree T,int i){
    if(T[2*i+1]!=Nil){
        InOrderTraverse(T,2*i+1);
    }
    cout<<T[i]<<‘ ‘;
    if(T[2*i+2]!=Nil){
        InOrderTraverse(T,2*i+2);
    }
}

//中序遍历
void PostOrderTraverse(SqBiTree T,int i){
    if(T[2*i+1]!=Nil){
        PostOrderTraverse(T,2*i+1);
    }
    if(T[2*i+2]!=Nil){
        PostOrderTraverse(T,2*i+2);
    }
    cout<<T[i]<<‘ ‘;
}

//层序遍历
void LevelOrderTraverse(SqBiTree T){
    int i=MAX_TREE_SIZE-1;
    while(T[i]==Nil){
        i--;
    }
    for(int j=0;j<=i;j++){
        if(T[j]!=Nil){
            cout<<T[j]<<‘ ‘;
        }
    }
    cout<<endl;
}

//逐层按本层序号输出二叉树
void Print(SqBiTree T){
    int j,k;
    position p;
    TElemType e;
    for(j=1;j<=BiTreeDepth(T);j++){
        cout<<"第"<<j<<"层: ";
        for(k=1;k<=pow(2,j-1);k++){
            p.level=j;
            p.order=k;
            e=GetValue(T,p);
            cout<<k<<":"<<e<<"     ";
        }
        cout<<endl;
    }
    cout<<endl;
}

  

时间: 2024-11-08 23:42:54

二叉树的基本操作(顺序二叉树)的相关文章

&lt;二叉树的基本操作&gt;

#include<stdio.h> #include<stdlib.h> #include<string.h> #define num 100 #define OK 1 typedef int Status; typedef char DataType; typedef struct node { DataType data; struct node *lchild,*rchild; }BinTNode,*BinTree; Status CreateBiTree(Bin

打印菜单界面,用c语言实现二叉树的基本操作

打印菜单界面,用c语言实现二叉树的基本操作: 其代码原理和用c++实现一样,请看本人上篇博客:二叉树的先序.中序.后序遍历等基本操作c++实现,链接:http://yaoyaolx.blog.51cto.com/10732111/1783527 实现代码: #include <stdio.h> #include <stdlib.h> #define MAXSIZE 50 //定义二叉树的二叉链表结构 typedef struct Node { char data; struct N

《二叉树的基本操作》

1 #include<stdio.h> 2 #include<stdlib.h> 3 #include<string.h> 4 5 #define NUM 100 //二叉树的最大结点数 6 #define QueueSize 100 //队列初始容量 7 #define TRUE 1 8 #define FALSE 0 9 #define OK 1 10 #define ERROR 0 11 #define OVERFLOW -1 12 13 typedef int

&lt;二叉树的基本操作(有层次遍历)&gt;

#include<stdio.h> #include<stdlib.h> #include<string.h> #define num 100 #define OK 1 #define ERROR 0 #define OVERFLOW -1 #define FALSE 0 #define TRUE 1 typedef int Status; typedef char DataType; typedef struct node { DataType data; struc

LeetCode 102 Binary Tree Level Order Traversal(二叉树的层级顺序遍历)(*)

翻译 给定一个二叉树,返回按层级顺序遍历的每个节点的值. 从左到右,逐层遍历. 例如: 给定一个二叉树 {3,9,20,#,#,15,7}, 3 / 9 20 / 15 7 返回它的层级顺序遍历结果为: [ [3], [9,20], [15,7] ] 翻译 Given a binary tree, return the level order traversal of its nodes' values. (ie, from left to right, level by level). For

二叉树的基本操作及应用(三)

#include <stdio.h> #include <stdlib.h> #include <malloc.h> #include <string.h> typedef char DataType; int depth=0; int h1=1; int nlayer=1; char ch2; typedef struct node { DataType data;//节点数据元素 struct node *lchild;//指向左孩子 struct no

C语言实现二叉树的基本操作

我在前面的博客中讲解了链表.栈和队列,这些数据结构其实都是线性表,并且给出了详细的实现.从今天开始,我们将要来学习树,树作为一种数据结构我们经常会用到,作为起步和基础,我们先来实现二叉树,也就是每个节点有不超过2个子节点的树.对于树的操作,最基本的创建.遍历.求树高.节点数等.代码上传至 https://github.com/chenyufeng1991/BinaryTree . (1)节点的定义 typedef int elemType; typedef struct BTNode{ elem

三叉链表实现二叉树的基本操作

三叉链表存储表示 改进于二叉链表,增加指向父节点的指针,能更好地实现结点间的访问. 存储结构 /* 二叉树的三叉链表存储表示 */ typedef struct BiTPNode { TElemType data; struct BiTPNode *parent,*lchild,*rchild; /* 双亲.左右孩子指针 */ }BiTPNode,*BiPTree; 下面给出二叉树采用三叉链表,实现了二叉树的构造.遍历.深度.宽度.结点个数.叶子个数 以及 结点的交换.层次.祖先.双亲.左孩子.

(转)数据结构:树、二叉树、最优二叉树

来源:http://www.cnblogs.com/coder2012/archive/2013/06/05/3102868.html 树 树形结构是一类非常重要的非线性结构,它可以很好地描述客观世界中广泛存在的具有分支关系或层次特性的对象,因此在计算机领域里有着广泛应用,如操作系统中的文件管理.编译程序中的语法结构和数据库系统信息组织形式等. 树的相关定义 节点的度:一个节点含有的子树的个数称为该节点的度: 树的度:一棵树中,最大的节点的度称为树的度: 叶节点或终端节点:度为零的节点: 非终端