实验三二叉树的基本操作

合集下载

二叉树的基本操作

二叉树的基本操作

二叉树的基本操作二叉树是一种常见的数据结构,它由节点组成,每个节点最多有两个子节点。

二叉树在计算机领域中得到广泛应用,它的基本操作包括插入、删除、查找、遍历等。

1.插入操作:二叉树的插入操作是将一个新的节点添加到已有的二叉树中的过程。

插入操作会按照一定规则将新节点放置在正确的位置上。

插入操作的具体步骤如下:-首先,从根节点开始,比较新节点的值与当前节点的值的大小关系。

-如果新节点的值小于当前节点的值,则将新节点插入到当前节点的左子树中。

-如果新节点的值大于当前节点的值,则将新节点插入到当前节点的右子树中。

-如果当前节点的左子树或右子树为空,则直接将新节点插入到该位置上。

-如果当前节点的左子树和右子树都不为空,则递归地对左子树或右子树进行插入操作。

2.删除操作:二叉树的删除操作是将指定节点从二叉树中删除的过程。

删除操作有以下几种情况需要考虑:-如果待删除节点是叶子节点,则直接将其从二叉树中删除即可。

-如果待删除节点只有一个子节点,则将其子节点替换为待删除节点的位置即可。

-如果待删除节点有两个子节点,则需要找到其左子树或右子树中的最大节点或最小节点,将其值替换为待删除节点的值,然后再删除最大节点或最小节点。

3.查找操作:二叉树的查找操作是在二叉树中查找指定值的节点的过程。

查找操作的具体步骤如下:-从根节点开始,将待查找值与当前节点的值进行比较。

-如果待查找值等于当前节点的值,则返回该节点。

-如果待查找值小于当前节点的值,则在当前节点的左子树中继续查找。

-如果待查找值大于当前节点的值,则在当前节点的右子树中继续查找。

-如果左子树或右子树为空,则说明在二叉树中找不到该值。

4.遍历操作:二叉树的遍历操作是按照一定规则依次访问二叉树中的每个节点。

有三种常用的遍历方式:- 前序遍历(Preorder Traversal):先访问根节点,然后递归地前序遍历左子树和右子树。

- 中序遍历(Inorder Traversal):先递归地中序遍历左子树,然后访问根节点,最后递归地中序遍历右子树。

(完整版)C++二叉树基本操作实验报告

(完整版)C++二叉树基本操作实验报告

一、实验目的选择二叉链式存储结构作为二叉树的存储结构,设计一个程序实现二叉树的基本操作(包括建立、输出、前序遍历、中序遍历、后序遍历、求树高、统计叶子总数等)二、实验开发环境Windows 8.1 中文版Microsoft Visual Studio 6.0三、实验内容程序的菜单功能项如下:1------建立一棵二叉树2------前序遍历递归算法3------前序遍历非递归算法4------中序遍历递归算法5------中序遍历非递归算法6------后序遍历递归算法7------后序遍历非递归算法8------求树高9------求叶子总数10-----输出二叉树11-----退出四、实验分析1、建立一棵二叉树2、输入二叉树各节点数据cout<<"请按正确顺序输入二叉树的数据:";cin.getline(t,1000); //先把输入的数据输入到一个t数组3、递归前序遍历void BL1(ECS_data *t){if(NULL!=t){cout<<t->data<<",";BL1(t->l);BL1(t->r);}}4、非递归前序遍历void preOrder2(ECS_data *t){stack<ECS_data*> s;ECS_data *p=t;while(p!=NULL||!s.empty()){while(p!=NULL){cout<<p->data<<" ";s.push(p);p=p->l;}if(!s.empty()){p=s.top();s.pop();p=p->r;}}}5、递归中序遍历void BL2(ECS_data *t){if(NULL!=t){BL2(t->l);cout<<t->data<<",";BL2(t->r);}}6、非递归中序遍历void inOrder2(ECS_data *t) //非递归中序遍历{stack<ECS_data*> s;ECS_data *p=t;while(p!=NULL||!s.empty()){while(p!=NULL){s.push(p);p=p->l;}if(!s.empty()){p=s.top();cout<<p->data<<" ";s.pop();p=p->r;}}}7、递归后序遍历void BL3(ECS_data *t){if(NULL!=t){BL3(t->l);BL3(t->r);cout<<t->data<<",";}}8、非递归后序遍历void postOrder3(ECS_data *t){stack<ECS_data*> s;ECS_data *cur; //当前结点ECS_data *pre=NULL; //前一次访问的结点s.push(t);while(!s.empty()){cur=s.top();if((cur->l==NULL&&cur->r==NULL)||(pre!=NULL&&(pre==cur->l||pre==cur->r))){cout<<cur->data<<" "; //如果当前结点没有孩子结点或者孩子节点都已被访问过s.pop();pre=cur;}else{if(cur->r!=NULL)s.push(cur->r);if(cur->l!=NULL)s.push(cur->l);}}}9、求树高int Height (ECS_data *t){if(t==NULL) return 0;else{int m = Height ( t->l );int n = Height(t->r);return (m > n) ? (m+1) : (n+1);}}10、求叶子总数int CountLeaf(ECS_data *t){static int LeafNum=0;//叶子初始数目为0,使用静态变量if(t)//树非空{if(t->l==NULL&&t->r==NULL)//为叶子结点LeafNum++;//叶子数目加1else//不为叶子结点{CountLeaf(t->l);//递归统计左子树叶子数目CountLeaf(t->r);//递归统计右子树叶子数目}}return LeafNum;}五、运行结果附:完整程序源代码://二叉树链式存储的实现#include<iostream>#include<cstring>#include <stack>using namespace std;struct ECS_data //先定义好一个数据的结构{char data;ECS_data *l;ECS_data *r;};class ECS{private://int level; //树高int n; //表示有多少个节点数int n1; //表示的是数组的总长度值,(包括#),因为后面要进行删除判断ECS_data *temp[1000];public:ECS_data *root;ECS() //初始化{ECS_data *p;char t[1000];int i;int front=0,rear=1; //front表示有多少个节点,rear表示当前插入的点的父母cout<<"请按正确顺序输入二叉树的数据:";cin.getline(t,1000); //先把输入的数据输入到一个t数组//cout<<t<<" "<<endl;int n1=strlen(t); //测量数据的长度n=0;for(i=0;i<n1;i++){if(t[i]!='#'){p=NULL;if(t[i]!=',') //满足条件并开辟内存{n++;p=new ECS_data;p->data=t[i];p->l=NULL;p->r=NULL;}front++;temp[front]=p;if(1 == front){root=p;}else{if((p!=NULL)&&(0==front%2)){temp[rear]->l=p;//刚开始把这里写成了==}if((p!=NULL)&&(1==front%2)){temp[rear]->r=p;}if(1==front%2)rear++; //就当前的数据找这个数据的父母}}}}~ECS() //释放内存{int i;for(i=1;i<=n;i++)if(temp[i]!=NULL)delete temp[i];}void JS() //记录节点的个数{int s;s=n;cout<<"该二叉树的节点数为:"<<s<<endl;}void BL1(ECS_data *t)//递归前序遍历{if(NULL!=t){cout<<t->data<<",";BL1(t->l);BL1(t->r);}}void preOrder2(ECS_data *t) //非递归前序遍历{stack<ECS_data*> s;ECS_data *p=t;while(p!=NULL||!s.empty()){while(p!=NULL){cout<<p->data<<" ";s.push(p);p=p->l;}if(!s.empty()){p=s.top();s.pop();p=p->r;}}}void BL2(ECS_data *t)//递归中序遍历{if(NULL!=t){BL2(t->l);cout<<t->data<<",";BL2(t->r);}}void inOrder2(ECS_data *t) //非递归中序遍历{stack<ECS_data*> s;ECS_data *p=t;while(p!=NULL||!s.empty()){while(p!=NULL){s.push(p);p=p->l;}if(!s.empty()){p=s.top();cout<<p->data<<" ";s.pop();p=p->r;}}}void BL3(ECS_data *t)//递归后序遍历{if(NULL!=t){BL3(t->l);BL3(t->r);cout<<t->data<<",";}}void postOrder3(ECS_data *t) //非递归后序遍历{stack<ECS_data*> s;ECS_data *cur; //当前结点ECS_data *pre=NULL; //前一次访问的结点s.push(t);while(!s.empty()){cur=s.top();if((cur->l==NULL&&cur->r==NULL)||(pre!=NULL&&(pre==cur->l||pre==cur->r))){cout<<cur->data<<" "; //如果当前结点没有孩子结点或者孩子节点都已被访问过s.pop();pre=cur;}else{if(cur->r!=NULL)s.push(cur->r);if(cur->l!=NULL)s.push(cur->l);}}}int Height (ECS_data *t) //求树高{if(t==NULL) return 0;else{int m = Height ( t->l );int n = Height(t->r);return (m > n) ? (m+1) : (n+1);}}int CountLeaf(ECS_data *t) //求叶子总数{static int LeafNum=0;//叶子初始数目为0,使用静态变量if(t)//树非空{if(t->l==NULL&&t->r==NULL)//为叶子结点LeafNum++;//叶子数目加1else//不为叶子结点{CountLeaf(t->l);//递归统计左子树叶子数目CountLeaf(t->r);//递归统计右子树叶子数目}}return LeafNum;}};int main(){ECS a;a.JS();cout<<"递归前序遍历:";a.BL1(a.root);cout<<endl;cout<<"非递归前序遍历:";a.preOrder2(a.root);cout<<endl;cout<<"递归中序遍历:";a.BL2(a.root);cout<<endl;cout<<"非递归中序遍历:";a.inOrder2(a.root);cout<<endl;cout<<"递归后序遍历:";a.BL3(a.root);cout<<endl;cout<<"非递归后序遍历:";a.postOrder3(a.root);cout<<endl;cout<<"树高为:"<<a.Height(a.root)<<endl;cout<<"叶子总数为:"<<a.CountLeaf(a.root)<<endl;return 0;}。

数据结构实验 二叉树的操作

数据结构实验 二叉树的操作

实验三二叉树的操作一、实验目的1、掌握二叉树的逻辑结构;2、掌握二叉树的二叉链表存储结构;3、掌握基于二叉链表存储的二叉树的遍历操作的实现。

二、实验内容1、采用二叉链表存储建立一棵含有n个结点的二叉树;2、前序打印该二叉树的所有叶子结点;3、统计该二叉树的结点个数;4、计算该二叉树的深度;5、交换该二叉树的所有左右子树。

三、程序实现1、二叉链表结点类型BiNode.htemplate<class T>struct BiNode{T data;BiNode<T> *lchild,*rchild;};2、二叉树的建立及操作BiTree.htemplate<class T>struct BiNode{T data;BiNode<T> *lchild,*rchild;};template <class T>class BiTree{public:BiTree( ); //构造函数,初始化一棵二叉树,其前序序列由键盘输入~BiTree(); //析构函数,释放二叉链表中各结点的存储空间BiNode<T>* Getroot(); //获得指向根结点的指针void PreOrder(BiNode<T> *root); //前序遍历二叉树void InOrder(BiNode<T> *root); //中序遍历二叉树void PostOrder(BiNode<T> *root); //后序遍历二叉树void LevelOrder(BiNode<T> *root); //层序遍历二叉树private:BiNode<T> *root; //指向根结点的头指针BiNode<T>* Creat(); //有参构造函数调用void Release(BiNode<T> *root); //析构函数调用};template<class T>BiTree<T>::BiTree(){cout<<"请按前根序输入该二叉树的各个结点(#号表示为空):\n";this->root=Creat();}template <class T>BiNode<T>* BiTree<T>::Creat(){BiNode<T> *root;T ch;cin>>ch;if (ch=='#') root = NULL;else{root = new BiNode<T>; //生成一个结点root->data=ch;root->lchild=Creat(); //递归建立左子树root->rchild=Creat(); //递归建立右子树}return root;}template<class T>BiTree<T>::~BiTree(){Release(root);}template<class T>BiNode<T>* BiTree<T>::Getroot( ){return root;}template<class T>void BiTree<T>::PreOrder(BiNode<T> *root){if(root==NULL) return;else{cout<<root->data<<" ";PreOrder(root->lchild);PreOrder(root->rchild);}}template <class T>void BiTree<T>::InOrder (BiNode<T> *root){if (root==NULL) return; //递归调用的结束条件else{InOrder(root->lchild); //中序递归遍历root的左子树cout<<root->data<<" "; //访问根结点的数据域InOrder(root->rchild); //中序递归遍历root的右子树}}template <class T>void BiTree<T>::PostOrder(BiNode<T> *root){if (root==NULL) return; //递归调用的结束条件else{PostOrder(root->lchild); //后序递归遍历root的左子树PostOrder(root->rchild); //后序递归遍历root的右子树cout<<root->data<<" "; //访问根结点的数据域}}template <class T>void BiTree<T>::LevelOrder(BiNode<T> *root){const int MaxSize = 100;int front = 0;int rear = 0; //采用顺序队列,并假定不会发生上溢BiNode<T>* Q[MaxSize];BiNode<T>* q;if (root==NULL) return;else{Q[rear++] = root;while (front != rear){q = Q[front++];cout<<q->data<<" ";if (q->lchild != NULL) Q[rear++] = q->lchild;if (q->rchild != NULL) Q[rear++] = q->rchild;}}}template<class T>void BiTree<T>::Release(BiNode<T>* root){if (root != NULL){Release(root->lchild); //释放左子树Release(root->rchild); //释放右子树delete root;}}3、主程序实现#include<iostream.h>#include "BiTree.h"int SumNode(BiNode<char> *root)//统计二叉树结点个数{int sum;if(root==NULL)return 0;else{sum=SumNode(root->lchild)+1;sum+=SumNode(root->rchild);return sum;}}void PrePrint(BiNode<char> *root)//前序打印二叉树叶子结点{if(root==NULL) return;else{if(root->lchild==NULL&&root->rchild==NULL)cout<<root->data<<' ';PrePrint(root->lchild);PrePrint(root->rchild);}}int TreeDeepth(BiNode<char> *root)//计算二叉树的深度{int deepth;if(root==NULL) return 0;else{deepth=(TreeDeepth(root->lchild)+1)>(TreeDeepth(root->rchild)+1)?(TreeDeepth(root->lchi ld)+1):(TreeDeepth(root->rchild)+1);return deepth;}}void Changechild(BiNode<char> *root)//交换二叉树的所有左右子树{BiNode<char> *temp;if(root==NULL||(root->lchild==NULL&&root->rchild==NULL)) return;else{Changechild(root->lchild);Changechild(root->rchild);if(root->lchild==NULL){root->lchild=root->rchild;root->rchild=NULL;}if(root->rchild==NULL){root->rchild=root->lchild;root->lchild=NULL;}else{temp=root->lchild;root->lchild=root->rchild;root->rchild=temp;}}}void main(){BiTree<char> Q;int deepth,sum;cout<<"Q的前序遍历为:\n";Q.PreOrder(Q.Getroot());cout<<"\nQ的中序遍历为:\n";Q.InOrder(Q.Getroot());cout<<"\nQ的后序遍历为:\n";Q.PostOrder(Q.Getroot());cout<<"\nQ的层序遍历为:\n";Q.LevelOrder(Q.Getroot());sum=SumNode(Q.Getroot());cout<<"\n结点个数为:"<<sum<<endl;deepth=TreeDeepth(Q.Getroot());cout<<"该二叉树的深度为:"<<deepth<<endl;cout<<"该二叉树叶子结点的前序打印顺序为:"<<'\n';PrePrint(Q.Getroot());cout<<"\n交换前二叉树的层序遍历为:\n";Q.LevelOrder(Q.Getroot());Changechild(Q.Getroot());cout<<"\n交换后二叉树的层序遍历为:\n";Q.LevelOrder(Q.Getroot());cout<<endl;}四、运行结果输入的二叉树结点的前根序序列为:ABDG##H##E#I##CF#J###二叉树形式为 AB CD E FG H I运行结果:五、实验心得体会通过本次实验过程,自己熟悉了二叉树的一些基本操作,掌握二叉树的逻辑结构;二叉树的二叉链表存储结构;熟悉了基于二叉链表存储的二叉树的遍历操作。

二叉树的基本操作实验报告

二叉树的基本操作实验报告

二叉树的基本操作实验报告学号姓名实验日期 2012-12-26实验室计算机软件技术实验指导教师设备编号 401实验内容二叉树的基本操作一实验题目实现二叉树的基本操作的代码实现二实验目的1、掌握二叉树的基本特性2、掌握二叉树的先序、中序、后序的递归遍历算法3、通过求二叉树的深度、度为2的结点数和叶子结点数等算法三实习要求(1)认真阅读书上给出的算法(2)编写程序并独立调试四、给出二叉树的抽象数据类型ADT BinaryTree{//数据对象D:D是具有相同特性的数据元素的集合。

//数据关系R:// 若D=Φ,则R=Φ,称BinaryTree为空二叉树;// 若D?Φ,则R={H},H是如下二元关系;// (1)在D中存在惟一的称为根的数据元素root,它在关系H下无前驱; // (2)若D-{root}?Φ,则存在D-{root}={D1,Dr},且D1?Dr =Φ; // (3)若D1?Φ,则D1中存在惟一的元素x1,<root,x1>?H,且存在D1上的关系H1 ?H;若Dr?Φ,则Dr中存在惟一的元素xr,<root,xr>?H,且存在上的关系Hr ?H;H={<root,x1>,<root,xr>,H1,Hr};// (4)(D1,{H1})是一棵符合本定义的二叉树,称为根的左子树;(Dr,{Hr})是一棵符合本定义的二叉树,称为根的右子树。

//基本操作:CreateBiTree( &T, definition ) // 初始条件:definition给出二叉树T的定义。

// 操作结果:按definiton构造二叉树T。

BiTreeDepth( T )// 初始条件:二叉树T存在。

// 操作结果:返回T的深度。

PreOrderTraverse( T, visit() ) // 初始条件:二叉树T存在,Visit是对结点操作的应用函数。

实验二 二叉树的基本操作

实验二    二叉树的基本操作

实验三二叉树的基本操作一、实验目的1、进一步掌握树的结构及非线性特点,递归特点和动态性。

2、掌握二叉树的建立算法。

3、掌握二叉树的三种遍历方法以及基于遍历的几种基本操作。

二、实验内容1、二叉树的链式存储结构的建立;2、二叉树的三种遍历算法以及基于遍历的几种操作的实现。

三、实验要求1、学生用C++/C完成算法设计和程序设计并上机调试通过;2、撰写实验报告,提供实验测试数据和实验结果;3、分析算法,要求给出具体的算法分析结果,包括时间复杂度和空间复杂度,并简要给出算法设计小结和心得。

四、实验准备1、了解树的结构特点及概念、二叉树的概念及结构特点。

2、了解树和二叉树的基本概念和术语。

3、二叉树的三种遍历方法(先序、中序、后序遍历)先序遍历:若二叉树为空,则空操作,否则①访问根结点;②先序遍历左子树;③先序遍历右子树。

中序遍历:若二叉树为空,则空操作,否则①中序遍历左子树;②访问根结点;③中序遍历右子树。

后序遍历:若二叉树为空,则空操作,否则①后序遍历左子树;②后序遍历右子树;③访问根结点。

4、二叉树的各种存储结构及其适用范围,特别是链式存储结构。

五、实验步骤1、编程实现二叉树的建立、遍历以及基于遍历的几种基本操作。

(1)采用二叉链表存储结构创建一个二叉树;(2)用递归方法实现二叉树的三种遍历算法(3)求二叉树中叶子结点的个数,度为1 的结点个数和度为2 的结点个数;(4)求二叉树的深度。

六、实验参考代码#include "iostream.h"#include "stdio.h"#include "stdlib.h"#define OK 1#define ERROR 0#define OVERFLOW -2#define NULL 0typedef char TElemType; //限定元素的数据类型typedef int Status;typedef struct BiTNode // 定义二叉树结点结构{TElemType data;BiTNode *lchild, *rchild; // 左右孩子指针} BiTNode, *BiTree;//按扩展的前序序列建立二叉树存储结构的算法Status CreateBiTree(BiTree &T){char ch;scanf("%c",&ch);if (ch=='#') T = NULL;else{if (!(T = (BiTNode *)malloc(sizeof(BiTNode)))) exit(OVERFLOW);T->data = ch; // 生成根结点CreateBiTree(T->lchild); // 构造左子树CreateBiTree(T->rchild); // 构造右子树}return OK;} // CreateBiTree// 先序遍历二叉树void PreOrder (BiTree T){if (T) {printf("%4c",T->data); // 访问结点PreOrder(T->lchild); // 遍历左子树PreOrder(T->rchild) ; // 遍历右子树}}// 中序遍历二叉树void InOrder (BiTree T){if (T){InOrder(T->lchild); // 遍历左子树printf("%4c",T->data); // 访问结点InOrder(T->rchild);// 遍历右子树}}// 后序遍历二叉树void PostOrder (BiTree T){if (T) {PostOrder (T->lchild); // 遍历左子树PostOrder (T->rchild);// 遍历右子树printf("%4c",T->data); // 访问结点}}//求二叉树的叶子结点数void CountLeaf (BiTree T, int& count){if(T){if((!T->lchild)&&(!T->rchild)) count++;CountLeaf(T->lchild,count);CountLeaf(T->rchild,count);}}//求二叉树中度为1的结点和度为2 的结点的数void CountBT(BiTree T,int &m,int &n){if(T){if((T->lchild!=0)&&(T->rchild!=0))n++; //度为2的结点else if(((T->lchild!=0)&&(T->rchild==0))||((T->lchild==0)&&(T->rchild!=0)))m++; //度为1 的结点CountBT (T->lchild,m,n);CountBT (T->rchild,m,n);}}//以下是求二叉树的深度int Depth (BiTree T ){int m,n;if(!T) return 0;else{m = Depth(T->lchild);n = Depth(T->rchild);return (m>n?m:n)+1;}}//主函数void main(){BiTree T;int s=0,m=0,n=0,d=0;T=NULL;int select;while(1) {printf("\n 请选择要执行的操作:\n");printf("1.创建二叉树\n");printf("2.二叉树的递归遍历算法(前、中、后)\n");printf("3.求二叉树的叶子结点数\n");printf("4.求二叉树的深度\n");printf("0.退出\n");scanf("%d",&select);getchar();switch(select) {case 0:return;case 1:printf("\n 请按先序次序输入各结点的值,以#表示空树:\n");CreateBiTree(T);printf("二叉树已建立完毕!\n");break;case 2:if(!T) printf("\n 未建立树,请先建树!\n");else {printf("\n 先序遍历:");PreOrder(T);printf("\n 中序遍历:");InOrder(T);printf("\n 后序遍历:");PostOrder(T);printf("\n");}break;case 3:if(!T) printf("\n 未建立树,请先建树!\n");else{CountLeaf(T,s);printf("\n 叶子结点数为:%d\n",s);CountBT(T,m,n);printf("度为1的结点数为:%d\n",m);printf("度为2 的结点数为:%d\n",n);}break;case 4:if(!T) printf("\n 未建立树,请先建树!\n");else{d=Depth(T);printf("\n 二叉树的深度为:%d\n",d);}break;default:printf("请确认选择项:\n");}//end switch}//end while}七、测试数据教材138 页,图7-10所示的二叉树按展的前序序列输入序列为:A B D # G # # # C E # # F H # # #。

数据结构实验3:二叉树的操作

数据结构实验3:二叉树的操作

TextFile中。

(4) P:打印代码文件(Print)。

将文件CodeFile以紧凑格式显示在终端上,每行50个代码。

同时将此字符形式的编码文件写入文件CodePrin中。

(5) T:打印哈夫曼树(Tree printing)。

将已在内存中的哈夫曼树以直观的方式显示在终端上,同时将此字符形式的哈夫曼树写入文件TreePrint中。

3) 实现提示:(1) 文件CodeFile的基类型可以设为字节型。

(2) 用户界面可以设计为“菜单”方式:显示上述功能符号,再加上“Q”,表示退出运行Quit。

请用户键入一个选择功能符。

此功能执行完毕后再显示此菜单,直至某次用户选择了“E”为止。

(3) 在程序的一次执行过程中,第一次执行I、D或C命令之后,哈夫曼树已经在内存了,不必再读入。

每次执行中不一定执行I命令,因为文件hfmTree可能早已建好。

三、实验过程与实验结果实验3-01:以二叉链表为存储结构,实现二叉树的创建、遍历数据结构定义:typedef struct BiTNode{char data;BiTNode *lchild, *rchild;}BiTNode;typedef BiTNode *BiTree;算法设计思路简介:本实验需要实现以下操作:二叉树的初始化、前中后序遍历等基本操作1.利用递归实现前后序遍历,思路简洁,仅需要调整递归体的执行顺序即可实现。

2.利用非递归实现中序遍历,需要利用栈操作,按照中序遍历规则将节点依次入栈后出栈实现。

算法描述:图1 中序遍历(非递归)实现算法的实现和测试结果(参考OJ)实验3-02:编写算法交换二叉树中所有结点的左、右子树数据结构定义:typedef struct BiTNode{char data;BiTNode *lchild, *rchild;}BiTNode;typedef BiTNode *BiTree;算法设计思路简介:本实验需要实现以下操作:二叉树的初始化、前中后序遍历等基本操作1.利用递归实现前后序遍历,思路简洁,仅需要调整递归体的执行顺序即可实现。

二叉树的各种基本运算的实现实验报告

二叉树的各种基本运算的实现实验报告

二叉树的各种基本运算的实现实验报告
一、实验目的
实验目的为了深入学习二叉树的各种基本运算,通过操作实现二叉树的建立、存储、查找、删除、遍历等各种基本运算操作。

二、实验内容
1、构造一个二叉树。

我们首先用一定的节点来构建一棵二叉树,包括节点的左子节点和右子节点。

2、实现查找二叉树中的节点。

在查找二叉树中的节点时,我们根据二叉树的特点,从根节点开始查找,根据要查找的节点的值与根节点的值的大小的关系,来决定接下来查找的方向,直到找到要查找的节点为止。

3、实现删除二叉树中的节点。

在删除二叉树节点时,我们要做的是找到要删除节点的父节点,然后让父节点的链接指向要删除节点的子节点,有可能要删除节点有一个子节点,有可能有两个极点,有可能没有子节点,我们要根据每种情况进行处理,来保持二叉树的结构不变。

4、对二叉树进行遍历操作。

二叉树的遍历有多种方法,本实验使用的是先序遍历。

首先从根节点出发,根据先序遍历的顺序,先访问左子树,然后再访问右子树,最后访问根节点。

三、实验步骤
1、构建二叉树:
我们用一个数组代表要构建的二叉树,第一项为根节点,第二项和第三项是根节点的子节点。

数据结构与算法实验——二叉树基本操作

数据结构与算法实验——二叉树基本操作

二叉树基本操作实验报告实验名称二叉树基本操作实验目的1.熟悉二叉树结点的结构和二叉树的基本操作;2.掌握二叉树每种操作的具体实现;3.学会利用递归方法编写对二叉树这种递归数据结构进行处理的算法;4.在二叉树基本操作的基础上掌握对二叉树的一些其它操作的具体实现方法;5.掌握构造哈夫曼树以及哈夫曼编码的方法。

实验内容编制一个演示二叉树创建、遍历、计算等操作的程序。

问题描述用数据结构相关知识,实现二叉树的定义和操作。

该程序包括二叉树结构类型以及对二叉树操作的具体的函数定义(包括:初始化二叉树、清空二叉树、检查二叉树是否为空、遍历二叉树(先序、后序、中序、层次)、求二叉树的深度、求二叉树所有节点数)。

问题分析该实验是基于C语言和数据结构知识基础的对二叉树的基本操作的检验,无需设计复杂的算法,程序语句也相对简单。

因此,我直接按要求定义了对二叉树操作的具体函数,并于主函数中实现对应的功能调用,其中,功能选择靠switch语句实现。

实验步骤1.需求分析本演示程序用VC++编写,完成二叉树的生成、遍历、计算等基本操作。

①输入的形式和输入值的范围:以字符(其中‘#’表示虚节点)的形式输入,以创建二叉树;在输入二叉树节点前,必须先确定该序列能正确创建二叉树。

②输出的形式:在所有三种操作中都显示操作是否正确以及操作后二叉树的内容。

③程序所能达到的功能:完成二叉树的生成、遍历(包括先序、后序、中序、层次四种方式)、计算等基本操作。

④测试数据:创建操作中依次输入a,b,d,#,g,#,#,#,c,e,#,#,f,#,#生成一个二叉树。

2.概要设计1)为了实现上述程序功能,需要定义二叉树的抽象数据类型:ADT BitTree {数据对象:由一个根节点和两个互不相交的左右子树构成数据关系:结点具有相同的数据类型及层次结构基本操作:Void BinTreeInit(BitTree *T)初始条件:无操作结果:初始化一棵二叉树Void BinTreeCreat(BitTree *T)初始条件:二叉树T已存在操作结果:按先序次序创建一棵二叉树2)本程序包含7个函数:①主函数main() ②初始化二叉树函数BinTreeInit() ③建立一棵二叉树函数BinTreeCreat() ④先序遍历函数PreOrderTraverse() ⑤中序遍历函数InOrderTraverse()⑥后序遍历函数PostOrderTraverse()⑦层次遍历函数LevelOrderTraverse()⑧求二叉树深度函数Countlevel()⑨检验空树函数BinTreeEmpty()⑩求节点数函数 Countnode()函数说明#include<stdio.h>#include<stdlib.h>typedef char Datatype;typedef struct NodeType{Datatype data;struct NodeType *lchild;struct NodeType *rchild;}BiTNode;typedef BiTNode * BinTree;//初始化二叉树。

实验3 二叉树的操作及应用

实验3 二叉树的操作及应用

实验3 二叉树的操作及应用PB13000818 焦孟娇实验目的:1. 熟练掌握递归程序设计的方法。

2. 掌握二叉树的特性和基本算法。

问题描述:二叉树是一种基本且常用的数据结构。

二叉树的很多基本算法都可以用递归的形式来表述。

本实验要求实现二叉树的如下操作:创建、销毁、复制、打印显示、先中后序遍历、查找元素、层序遍历、求二叉树的深度、宽度、结点数和叶子个数等。

实验内容:一、队列的抽象数据类型定义为:Queue operation{数据对象:数据关系:基本操作:InitQueue(&S)操作结果:构造一个空队列SQueueLength(S)初始条件:队列S已存在操作结果:返回S的元素个数,即队列的长度QueueEmpty(S)初始条件:队列S已存在操作结果:若S为空队列,则返回TRUE,否则FALSEEnQueue(&S, e)初始条件:队列S已存在操作结果:插入元素e为队列新元素DeQueue(&S, &e)初始条件:队列S已存在且非空操作结果:删除S的队头元素,并用e返回其值GetHead(S, &e)初始条件:队列S已存在且非空操作结果:用e返回S的队头元素ClearQueue(&S)初始条件:队列S已存在操作结果:将S清为空队列DeleteQueue(&S)初始条件:队列S已存在操作结果:队列S被销毁Print(S)初始条件:队列S已存在操作结果:输出队列S} Queue operationBiTree operation{InitBiTree( &T )// 操作结果:构造空二叉树T。

DestroyBiTree( &T )// 初始条件:二叉树T已存在。

// 操作结果:销毁二叉树T。

CreateBiTree( &T, definition )// 初始条件:definition给出二叉树T的定义。

// 操作结果:按definiton构造二叉树T。

数据结构实验三——二叉树基本操作及运算实验报告

数据结构实验三——二叉树基本操作及运算实验报告

《数据结构与数据库》实验报告实验题目二叉树的基本操作及运算一、需要分析问题描述:实现二叉树(包括二叉排序树)的建立,并实现先序、中序、后序和按层次遍历,计算叶子结点数、树的深度、树的宽度,求树的非空子孙结点个数、度为2的结点数目、度为2的结点数目,以及二叉树常用运算。

问题分析:二叉树树型结构是一类重要的非线性数据结构,对它的熟练掌握是学习数据结构的基本要求。

由于二叉树的定义本身就是一种递归定义,所以二叉树的一些基本操作也可采用递归调用的方法。

处理本问题,我觉得应该:1、建立二叉树;2、通过递归方法来遍历(先序、中序和后序)二叉树;3、通过队列应用来实现对二叉树的层次遍历;4、借用递归方法对二叉树进行一些基本操作,如:求叶子数、树的深度宽度等;5、运用广义表对二叉树进行广义表形式的打印。

算法规定:输入形式:为了方便操作,规定二叉树的元素类型都为字符型,允许各种字符类型的输入,没有元素的结点以空格输入表示,并且本实验是以先序顺序输入的。

输出形式:通过先序、中序和后序遍历的方法对树的各字符型元素进行遍历打印,再以广义表形式进行打印。

对二叉树的一些运算结果以整型输出。

程序功能:实现对二叉树的先序、中序和后序遍历,层次遍历。

计算叶子结点数、树的深度、树的宽度,求树的非空子孙结点个数、度为2的结点数目、度为2的结点数目。

对二叉树的某个元素进行查找,对二叉树的某个结点进行删除。

测试数据:输入一:ABC□□DE□G□□F□□□(以□表示空格),查找5,删除E预测结果:先序遍历ABCDEGF中序遍历CBEGDFA后序遍历CGEFDBA层次遍历ABCDEFG广义表打印A(B(C,D(E(,G),F)))叶子数3 深度5 宽度2 非空子孙数6 度为2的数目2 度为1的数目2查找5,成功,查找的元素为E删除E后,以广义表形式打印A(B(C,D(,F)))输入二:ABD□□EH□□□CF□G□□□(以□表示空格),查找10,删除B预测结果:先序遍历ABDEHCFG中序遍历DBHEAGFC后序遍历DHEBGFCA层次遍历ABCDEFHG广义表打印A(B(D,E(H)),C(F(,G)))叶子数3 深度4 宽度3 非空子孙数7 度为2的数目2 度为1的数目3查找10,失败。

实验三二叉树的基本操作

实验三二叉树的基本操作

实验三二叉树的基本运算一、实验目的1、使学生熟练掌握二叉树的逻辑结构和存储结构。

2、熟练掌握二叉树的各种遍历算法。

二、实验内容题目一:二叉树的基本操作实现(必做题)[ 问题描述]建立一棵二叉树,试编程实现二叉树的如下基本操作:1. 按先序序列构造一棵二叉链表表示的二叉树T;2. 对这棵二叉树进行遍历:先序、中序、后序以及层次遍历,分别输出结点的遍历序列;3. 求二叉树的深度/结点数目/叶结点数目;(选做)4. 将二叉树每个结点的左右子树交换位置。

(选做)[ 基本要求]从键盘接受输入(先序),以二叉链表作为存储结构,建立二叉树(以先序来建立),[ 测试数据]如输入:AB($巾D邱毋巾F巾巾巾(其中巾表示空格字符)则输出结果为先序:ABCDEGF中序:CBEGDFA后序:CGEFDBA层序:ABCDEFG[ 选作内容]采用非递归算法实现二叉树遍历三、算法设计1、 主要思想:根据二叉树的图形结构创建出二叉树的数据结构, 用指针对树进行操作,重点掌握二叉树的结构和性质。

2、 本程序包含四个模块:然后 (1)结构体定义(2) 创建二叉树(3) 对树的几个操作(4) 主函数四、调试分析这是一个比较简单程序,调试过程中并没有出现什么问题,思路比较清晰五、实验结果六、总结此次上机实验对二叉树进行了以一次实际操作,让我对二叉树 有了更深的了解,对二叉树的特性有了更熟悉的认知,让我知道了二叉树的重要性和便利性,这对以后的编程有更好的帮助。

七、源程序#in clude <iostream>#in clude <queue>using namespacestd;#defi ne TElemType char#defi ne Status int#defi ne OK1#defi ne ERRORtypedef struct BiTNode{TEIemTypedata;struct BiTNode * Ichild, *rchild;} BiTNode,* BiTree ;Status CreateBiTree( BiTree &T) {TElemTypech;cin >> ch;if (ch == '#')T = NULLelse{if (!( T = ( BiTNode *)malloc( sizeof (BiTNode))))exit( OVERFLOW「>data = ch;CreateBiTree( T->lchild);CreateBiTree( T->rchild);}return OKStatus PreOrderTraverse( BiTree T){if ( T){cout << T->data;if (PreOrderTraverse( T->lchild))if (PreOrderTraverse( T->rchild))return OKreturn ERRQR}elsereturn OK}Status InOrderTraverse( BiTree T){if ( T) In OrderTraverse( T->lchild); cout << T->data;In OrderTraverse( T->rchild);}return OK}Status PostOrderTraverse( BiTree T){if ( T){PostOrderTraverse( T->lchild);PostOrderTraverse( T->rchild); cout << T->data;}return OK}Status leOrderTraverse( BiTree T){std:: queuevBiTree > Q;if ( T == NULI) return ERRQRelse {Q.push( T);while (!Q.empty()){T = Q.fron t();Q.pop();NULI) cout << T->data;if ( T->lchild != NULLQ.push(T->lchild);if ( T->rchild != NULLQ.push( T->rchild);}}return OK}Status change( BiTree T){BiTree temp = NULLif ( T->lchild == NULL&& T->rchild ==return OKelse {temp = T->lchild;T->lchild = T->rchild;T->rchild = temp;if ( T->lchild)cha nge(「>lchild);if ( T->rchild)cha nge(「>rchild);return OK}:rchilddeep + 1; int FindTreeDeep( BiTree T){int deep = 0;if ( T){int lchilddeep = FindTreeDeep( T->lchild);int rchilddeep = FindTreeDeep( T->rchild);deep = lchilddeep >= rchilddeep ? lchilddeep + 1 }return deep;}int main(){BiTree T;CreateBiTree(T);cout << "先序遍历顺序为:";PreOrderTraverse(T);cout << en dl;cout << "中序遍历顺序为:”;InO rderTraverse(T);cout << en dl;cout << "后序遍历顺序为:”;PostOrderTraverse(T);cout << en dl;cout << "层序遍历顺序为:";leOrderTraverse(T);cout << en dl;cout << "二叉树深度为:"<< Fi ndTreeDeep(T)«e ndl;cout << "左右子树交换后:";cha nge(T);cout << "先序遍历顺序为:";PreOrderTraverse(T); |cout << en dl;return 0;}。

实验三 二叉树的基本操作实现及其应用

实验三    二叉树的基本操作实现及其应用

二叉树的基本操作实现及其应用一、实验目的1.熟悉二叉树结点的结构和对二叉树的基本操作。

2.掌握对二叉树每一种操作的具体实现。

3.学会利用递归方法编写对二叉树这种递归数据结构进行处理的算法。

4.会用二叉树解决简单的实际问题。

二、实验内容设计程序实现二叉树结点的类型定义和对二叉树的基本操作。

该程序包括二叉树结构类型以及每一种操作的具体的函数定义和主函数。

1 按先序次序建立一个二叉树,2按(A:先序 B:中序 C:后序)遍历输出二叉树的所有结点以上比做,以下选做3求二叉树中所有结点数4求二叉树的深度三、实验步骤㈠、数据结构与核心算法的设计描述/* 定义DataType为char类型 */typedef char DataType;/* 二叉树的结点类型 */typedef struct BitNode{ DataType data;struct BitNode *lchild,*rchild;}*BitTree;相关函数声明:1、/* 初始化二叉树,即把树根指针置空 */void BinTreeInit(BitTree *BT){BT=(BitTree)malloc(sizeof(BitNode));BT->data=NULL;cout<<"二叉树初始化成功!"<<endl;}2、/* 按先序次序建立一个二叉树*/int BinTreeCreat(BitTree &BT){char ch;cin>>ch;if(ch=='#') BT=NULL;else{if(!(BT=(BitTree)malloc(sizeof(BitNode))))exit(0);BT->data=ch;BinTreeCreat(BT->lchild);BinTreeCreat(BT->rchild);}return 0;}3、/* 检查二叉树是否为空 */void BinTreeEmpty(BitTree &BT){if(BT->data==NULL)cout<<"是空二叉树!"<<endl;elsecout<<"不是空二叉树!"<<endl;}4、/*按任一种遍历次序(包括按先序、中序、后序、按层次)输出二叉树中的所有结点 */void BinTraverse(BitTree &BT)//按先序序列建立二叉树{if(BT!=NULL){cout<<BT->data;BinTraverse(BT->lchild);BinTraverse(BT->rchild);}}5、/* 求二叉树的深度 */int BinTreeDepth(BitTree BT){int depthval;if(BT){int depthLeft=BinTreeDepth(BT->lchild);int depthRight=BinTreeDepth(BT->rchild);depthval=1+(depthLeft>depthRight?depthLeft:depthRight);}else depthval=0;return depthval;}6、/* 求二叉树中所有结点数 */int BinTreeCount(BitTree BT){int node;if(BT){int lchild=BinTreeCount(BT->lchild);int rchild=BinTreeCount(BT->rchild);node=lchild+rchild+1;}elsenode=0;return node;}㈡、函数调用及主函数设计㈢程序调试及运行结果分析测试数据: 1、初始化二叉树; 2、按先序序列建立二叉树;3、判断二叉树是否为空;4、先序序列遍历二叉树;5、求二叉树的深度;6、求二叉树节点的个数。

二叉树实验报告

二叉树实验报告

二叉树实验报告1. 引言二叉树是一种常用的数据结构,广泛应用于计算机科学和信息技术领域。

本实验旨在通过对二叉树的理解和实现,加深对数据结构与算法的认识和应用能力。

本报告将介绍二叉树的定义、基本操作以及实验过程中的设计和实现。

2. 二叉树的定义二叉树是一个有序树,其每个节点最多有两个子节点。

树的左子节点和右子节点被称为二叉树的左子树和右子树。

3. 二叉树的基本操作3.1 二叉树的创建在实验中,我们通过定义一个二叉树的节点结构来创建一个二叉树。

节点结构包含一个数据域和左右指针,用于指向左右子节点。

创建二叉树的过程可以通过递归或者迭代的方式来完成。

3.2 二叉树的插入和删除二叉树的插入操作是将新节点插入到树中的合适位置。

插入时需要考虑保持二叉树的有序性。

删除操作是将指定节点从树中删除,并保持二叉树的有序性。

在实验中,我们可以使用递归或者循环的方式实现这些操作。

3.3 二叉树的遍历二叉树的遍历是指按照某种次序访问二叉树的所有节点。

常见的遍历方式包括前序遍历、中序遍历和后序遍历。

前序遍历先访问根节点,然后按照左孩子-右孩子的顺序递归遍历左右子树。

中序遍历按照左孩子-根节点-右孩子的顺序递归遍历左右子树。

后序遍历按照左孩子-右孩子-根节点的顺序递归遍历左右子树。

3.4 二叉树的查找查找操作是指在二叉树中查找指定的值。

可以通过递归或者循环的方式实现二叉树的查找操作。

基本思路是从根节点开始,通过比较节点的值和目标值的大小关系,逐步向左子树或者右子树进行查找,直到找到目标节点或者遍历到叶子节点。

4. 实验设计和实现在本实验中,我们设计并实现了一个基于Python语言的二叉树类。

具体实现包括二叉树的创建、插入、删除、遍历和查找操作。

在实验过程中,我们运用了递归和迭代的方法实现了这些操作,并进行了测试和验证。

4.1 二叉树类的设计我们将二叉树的节点设计为一个类,其中包括数据域和左右子节点的指针。

另外,我们设计了一个二叉树类,包含了二叉树的基本操作方法。

二叉树基本操作--实验报告

二叉树基本操作--实验报告

⼆叉树基本操作--实验报告实验三⼆叉树的基本操作学院:物理与电⼦学院班级:电信1105班姓名:刘岩学号:29⼀、实验⽬的1、熟悉⼆叉树的基本操作,掌握⼆叉树的实现以及实际应⽤。

3、加深对于⼆叉树的理解,逐步培养解决实际问题的编程能⼒。

⼆、实验环境1台WINDOWS环境的PC机,装有Visual C++ 。

三、实验内容1、问题描述现需要编写⼀套⼆叉树的操作函数,以便⽤户能够⽅便的利⽤这些函数来实现⾃⼰的应⽤。

其中操作函数包括:1>创建⼆叉树CreateBTNode(*b,*str):根据⼆叉树括号表⽰法的字符串*str⽣成对应的链式存储结构。

2>输出⼆叉树DispBTNode(*b):以括号表⽰法输出⼀棵⼆叉树。

3>查找结点FindNode(*b,x):在⼆叉树b中寻找data域值为x的结点,并返回指向该结点的指针。

4>求⾼度BTNodeDepth(*b):求⼆叉树b的⾼度。

若⼆叉树为空,则其⾼度为0;否则,其⾼度等于左⼦树与右⼦树中的最⼤⾼度加l。

5>求⼆叉树的结点个数NodesCount(BTNode *b)6>先序遍历的递归算法:void PreOrder(BTNode *b)7>中序遍历的递归算法:void InOrder(BTNode *b)8>后序遍历递归算法:void PostOrder(BTNode *b)9>层次遍历算法void LevelOrder(BTNode *b)2、基本要求实现以上9个函数。

主函数中实现以下功能:创建下图中的树b输出⼆叉树b找到’H’节点,输出其左右孩⼦值输出b的⾼度输出b的节点个数输出b的四种遍历顺序3、程序编写上图转化为⼆叉树括号表⽰法为A(B(D,E(H(J,K(L,M(,N))))),C(F,G(,I)))程序:#include <>#include <>#define MaxSize 100typedef char ElemType;typedef struct node{ElemType data; /*数据元素*/struct node *lchild; /*指向左孩⼦*/struct node *rchild; /*指向右孩⼦*/} BTNode;void CreateBTNode(BTNode *&b,char *str);//创建BTNode *FindNode(BTNode *b,ElemType x);//查找节点int BTNodeHeight(BTNode *b);//求⾼度void DispBTNode(BTNode *b);//输出int NodesCount(BTNode *b);//⼆叉树的结点个数void PreOrder(BTNode *b);//先序遍历递归void InOrder(BTNode *b);//中序遍历递归void PostOrder(BTNode *b);//后序遍历递归void LevelOrder(BTNode *b);//层次遍历//创建void CreateBTNode(BTNode *&b,char *str){BTNode *St[MaxSize],*p=NULL;int top=-1,k,j=0;char ch;b=NULL;ch=str[j];while(ch!='\0'){switch(ch){case '(':top++;St[top]=p;k=1;break;case ')':top--;break;case ',':k=2;break;default:p=(BTNode *)malloc(sizeof(BTNode)); p->data=ch;p->lchild=p->rchild=NULL;if(b==NULL)b=p;else{switch(k){case 1:St[top]->lchild=p;break;case 2:St[top]->rchild=p;break;}}}j++;ch=str[j];}}//输出void DispBTNode(BTNode *b){if(b!=NULL){printf("%c",b->data);if(b->lchild!=NULL||b->rchild!=NULL){printf("(");DispBTNode(b->lchild);if(b->rchild!=NULL)printf(",");DispBTNode(b->rchild);printf(")");}}}//查找节点BTNode *FindNode(BTNode *b,ElemType x){ BTNode *p;if(b==NULL)return b;else if(b->data==x)return b;else{p=FindNode(b->lchild,x);if(p!=NULL)return p;elsereturn FindNode(b->rchild,x);}}//求⾼度int BTNodeHeight(BTNode *b){int lchildh,rchildh;if(b==NULL)return (0);else{lchildh=BTNodeHeight(b->lchild);rchildh=BTNodeHeight(b->rchild);return(lchildh>rchildh)(lchildh+1):(rchildh+1);}}//⼆叉树的结点个数int NodesCount(BTNode *b){if(b==NULL)return 0;elsereturn NodesCount(b->lchild)+NodesCount(b->rchild)+1; }//先序遍历递归void PreOrder(BTNode *b){ if(b!=NULL){printf("%c",b->data); PreOrder(b->lchild); PreOrder(b->rchild);}}//中序遍历递归void InOrder(BTNode *b){if(b!=NULL){InOrder(b->lchild);printf("%c",b->data); InOrder(b->rchild);}}//后序遍历递归void PostOrder(BTNode *b){ if(b!=NULL){PostOrder(b->lchild); PostOrder(b->rchild);printf("%c",b->data);}}//层次遍历void LevelOrder(BTNode *b){ BTNode *p;BTNode *qu[MaxSize];int front,rear;front=rear=-1;rear++;qu[rear]=b;while(front!=rear){front=(front+1)%MaxSize;p=qu[front];printf("%c",p->data);if(p->lchild!=NULL){rear=(rear+1)%MaxSize;qu[rear]=p->lchild;}if(p->rchild!=NULL){rear=(rear+1)%MaxSize;qu[rear]=p->rchild;}}}void main(){BTNode *b,*p,*lp,*rp;char str[]="A(B(D,E(H(J,K(L,M(,N))))),C(F,G(,I)))";//根据树形图改写成的//⼆叉树括号表⽰法的字符串*str //char str[100];scanf("%s",&str);//⾃⾏输⼊括号表⽰的⼆叉树CreateBTNode(b,str); //创建树bprintf("\n");printf("输出⼆叉树:");//输出⼆叉树bDispBTNode(b);printf("\n");printf("'H'结点:");//找到'H'节点,输出其左右孩⼦值p=FindNode(b,'H');printf("\n");if (p!=NULL){printf("左孩⼦节点的值");printf("%c",p->lchild->data);printf("\n");printf("右孩⼦节点的值");printf("%c",p->rchild->data);printf("\n");//此处输出p的左右孩⼦节点的值}printf("\n");printf("⼆叉树b的深度:%d\n",BTNodeHeight(b));//输出b的⾼度printf("⼆叉树b的结点个数:%d\n",NodesCount(b));//输出b的节点个数printf("\n");printf(" 先序遍历序列:\n");//输出b的四种遍历顺序printf(" 算法:");PreOrder(b);printf("\n");printf(" 中序遍历序列:\n");printf(" 算法:");InOrder(b);printf("\n");printf(" 后序遍历序列:\n");printf(" 算法:");PostOrder(b);printf("\n");printf(" 层次遍历序列:\n");printf(" 算法:");LevelOrder(b); printf("\n");}四、实验⼼得与⼩结通过本次实验,我熟悉⼆叉树的基本知识内容,对课本的知识有了更加深刻的理解与掌握掌握。

二叉树的基本操作与实现实验报告

二叉树的基本操作与实现实验报告

二叉树的基本操作与实现实验报告二叉树是一种重要的数据结构,在计算机科学领域中被广泛应用。

本实验将介绍二叉树的基本操作与实现,并给出相应的实验报告。

一、引言二叉树是一种特殊的树状结构,每个节点至多有两个子节点。

二叉树有许多重要的特性,如平衡二叉树、二叉树等,应用广泛。

在本实验中,我们将介绍二叉树的基本操作和实现。

二、实验目的1.掌握二叉树的基本概念和特性;2.熟悉二叉树的基本操作,包括创建、插入、删除、遍历等;3.学会使用编程语言实现二叉树的基本操作。

三、实验内容本实验主要包括以下内容:1.二叉树的定义和基本概念;2.二叉树的基本操作,包括创建、插入、删除、遍历等;3.使用编程语言实现二叉树的基本操作;4.测试和验证二叉树的基本操作的正确性。

四、实验步骤1.二叉树的定义和基本概念二叉树是一种树状结构,每个节点至多有两个子节点。

二叉树的每个节点包含一个数据项和指向左子树和右子树的指针。

二叉树的特性有很多,如完全二叉树、平衡二叉树、二叉树等。

2.二叉树的基本操作(1)创建二叉树:可以通过手动输入节点数据来创建二叉树,也可以通过读取文件中的数据来创建二叉树。

(2)插入节点:在指定位置插入一个新节点。

(3)删除节点:删除指定位置的节点。

(4)遍历二叉树:有前序遍历、中序遍历和后序遍历三种遍历方式。

3.使用编程语言实现二叉树的基本操作实现二叉树的基本操作可以使用编程语言来完成。

我们可以定义一个二叉树的结构体,包含节点数据和指向左右子树的指针。

然后根据具体的需求,实现相应的操作函数。

4.测试和验证二叉树的基本操作的正确性在完成二叉树的基本操作后,我们可以编写测试代码来验证操作的正确性。

通过创建二叉树,并进行插入、删除和遍历操作,观察输出结果是否符合预期。

五、实验结果与分析在完成二叉树的基本操作后,我们可以进行测试和验证。

通过输出二叉树的遍历结果,比对预期结果来判断操作是否正确。

同时,我们还可以观察二叉树的结构和特性,如是否满足平衡二叉树或二叉树的条件。

数据结构实验报告(二叉树的基本操作)

数据结构实验报告(二叉树的基本操作)
else if((root->LChild==NULL)&&(root->RChild==NULL)) LeafNum=1;
else LeafNum=LeafCount(root->LChild)+LeafCount(root->RChild);
//叶子数为左右子树数目之和
return LeafNum;
printf("\n菜单选择\n\n");
printf(" 1.树状输出二叉树2.先序遍历二叉树\n");
printf(" 3.中序遍历二叉树4.后序遍历二叉树\n");
printf(" 5.输出叶子结点6.输出叶子结点的个数\n");
printf(" 7.输出二叉树的深度8.退出\n");
printf("\n----------------------------------------------------------------------\n");
{
printf("\n\n");
j=j+1; k=0;
while(k<nlocate)
{
printf(" ");
k++;
}
}
while(k<(nlocate-1))
{
printf(" ");
k++;
}
printf("%c",bt->data );
q.front=q.front+1;
if(bt->LChild !=NULL)//存在左子树,将左子树根节点入队列

二叉树的基本操作

二叉树的基本操作

二叉树的基本操作二叉树是一种常见的数据结构,它由节点组成,每个节点最多连接两个子节点,分别称为左子节点和右子节点。

二叉树的基本操作包括创建、插入、删除、查找和遍历,下面将对这些操作进行详细介绍。

一、创建二叉树创建二叉树的方法有多种,其中最常用的是使用递归的方式。

递归创建二叉树时,可以先创建根节点,然后递归创建左子树和右子树。

如果子树为空,则使用特殊字符表示。

二、插入节点插入节点是向二叉树中添加新节点的操作。

插入节点的位置通常由二叉树的特性决定,左子节点小于父节点,右子节点大于父节点。

插入节点时,需要先找到插入位置,然后创建新节点,并将其连接到对应的位置。

三、删除节点删除节点是从二叉树中移除指定节点的操作。

删除节点的方式取决于节点的位置和子节点的情况。

如果要删除的节点是叶子节点,则直接将其删除即可。

如果要删除的节点有一个子节点,则将其子节点连接到父节点。

如果要删除的节点有两个子节点,则需要找到替代节点,将替代节点的值复制到当前位置,并将替代节点删除。

四、查找节点查找节点是在二叉树中寻找特定节点的操作。

常用的方式有深度优先(DFS)和广度优先(BFS)。

深度优先通常使用递归实现,分为前序遍历、中序遍历和后序遍历三种方式。

广度优先通常使用队列实现,先访问根节点,然后访问其所有子节点,再逐层访问下去,直到找到目标节点或遍历完整棵树。

五、遍历二叉树遍历二叉树是指按照一定顺序访问二叉树中的所有节点,常用的方式有前序遍历、中序遍历和后序遍历。

前序遍历先访问根节点,然后递归遍历左子树和右子树;中序遍历先递归遍历左子树,然后访问根节点,再遍历右子树;后序遍历先递归遍历左子树和右子树,然后访问根节点。

以上是二叉树的基本操作,通过这些操作可以有效地管理和处理二叉树数据结构。

在实际应用中,二叉树常用于、排序和表达等方面,因为它具有较高的查询效率和灵活性。

对于使用二叉树的相关算法和数据结构,理解和掌握其基本操作是非常重要的。

二叉树基本操作--实验报告材料

二叉树基本操作--实验报告材料

实验三二叉树的基本操作学院:物理与电子学院班级:电信1105班姓名:刘岩学号:1404110729一、实验目的1、熟悉二叉树的基本操作,掌握二叉树的实现以及实际应用。

3、加深对于二叉树的理解,逐步培养解决实际问题的编程能力。

二、实验环境1台WINDOWS环境的PC机,装有Visual C++ 6.0。

三、实验内容1、问题描述现需要编写一套二叉树的操作函数,以便用户能够方便的利用这些函数来实现自己的应用。

其中操作函数包括:1>创建二叉树CreateBTNode(*b,*str):根据二叉树括号表示法的字符串*str生成对应的链式存储结构。

2>输出二叉树DispBTNode(*b):以括号表示法输出一棵二叉树。

3>查找结点FindNode(*b,x):在二叉树b中寻找data域值为x的结点,并返回指向该结点的指针。

4>求高度BTNodeDepth(*b):求二叉树b的高度。

若二叉树为空,则其高度为0;否则,其高度等于左子树与右子树中的最大高度加l。

5>求二叉树的结点个数NodesCount(BTNode *b)6>先序遍历的递归算法:void PreOrder(BTNode *b)7>中序遍历的递归算法:void InOrder(BTNode *b)8>后序遍历递归算法:void PostOrder(BTNode *b)9>层次遍历算法void LevelOrder(BTNode *b)2、基本要求实现以上9个函数。

主函数中实现以下功能:创建下图中的树b输出二叉树b找到’H’节点,输出其左右孩子值输出b的高度输出b的节点个数输出b的四种遍历顺序3、程序编写上图转化为二叉树括号表示法为A(B(D,E(H(J,K(L,M(,N))))),C(F,G(,I)))程序:#include <stdio.h>#include <malloc.h>#define MaxSize 100typedef char ElemType;typedef struct node{ElemType data; /*数据元素*/struct node *lchild; /*指向左孩子*/struct node *rchild; /*指向右孩子*/} BTNode;void CreateBTNode(BTNode *&b,char *str);//创建BTNode *FindNode(BTNode *b,ElemType x);//查找节点int BTNodeHeight(BTNode *b);//求高度void DispBTNode(BTNode *b);//输出int NodesCount(BTNode *b);//二叉树的结点个数void PreOrder(BTNode *b);//先序遍历递归void InOrder(BTNode *b);//中序遍历递归void PostOrder(BTNode *b);//后序遍历递归void LevelOrder(BTNode *b);//层次遍历//创建void CreateBTNode(BTNode *&b,char *str){BTNode *St[MaxSize],*p=NULL;int top=-1,k,j=0;char ch;b=NULL;ch=str[j];while(ch!='\0'){switch(ch){case '(':top++;St[top]=p;k=1;break;case ')':top--;break;case ',':k=2;break;default:p=(BTNode *)malloc(sizeof(BTNode));p->data=ch;p->lchild=p->rchild=NULL;if(b==NULL)b=p;else{switch(k){case 1:St[top]->lchild=p;break;case 2:St[top]->rchild=p;break;}}}j++;ch=str[j];}}//输出void DispBTNode(BTNode *b){if(b!=NULL){printf("%c",b->data);if(b->lchild!=NULL||b->rchild!=NULL){printf("(");DispBTNode(b->lchild);if(b->rchild!=NULL)printf(",");DispBTNode(b->rchild);printf(")");}}}//查找节点BTNode *FindNode(BTNode *b,ElemType x){BTNode *p;if(b==NULL)return b;else if(b->data==x)return b;else{p=FindNode(b->lchild,x);if(p!=NULL)return p;elsereturn FindNode(b->rchild,x);}}//求高度int BTNodeHeight(BTNode *b){int lchildh,rchildh;if(b==NULL)return (0);else{lchildh=BTNodeHeight(b->lchild);rchildh=BTNodeHeight(b->rchild);return(lchildh>rchildh)?(lchildh+1):(rchildh+1);}}//二叉树的结点个数int NodesCount(BTNode *b){if(b==NULL)return 0;elsereturn NodesCount(b->lchild)+NodesCount(b->rchild)+1;}//先序遍历递归void PreOrder(BTNode *b){if(b!=NULL){printf("%c",b->data);PreOrder(b->lchild);PreOrder(b->rchild);}}//中序遍历递归void InOrder(BTNode *b){if(b!=NULL){InOrder(b->lchild);printf("%c",b->data);InOrder(b->rchild);}}//后序遍历递归void PostOrder(BTNode *b){if(b!=NULL){PostOrder(b->lchild);PostOrder(b->rchild);printf("%c",b->data);}}//层次遍历void LevelOrder(BTNode *b){BTNode *p;BTNode *qu[MaxSize];int front,rear;front=rear=-1;rear++;qu[rear]=b;while(front!=rear){front=(front+1)%MaxSize;p=qu[front];printf("%c",p->data);if(p->lchild!=NULL){rear=(rear+1)%MaxSize;qu[rear]=p->lchild;}if(p->rchild!=NULL){rear=(rear+1)%MaxSize;qu[rear]=p->rchild;}}}void main(){BTNode *b,*p,*lp,*rp;char str[]="A(B(D,E(H(J,K(L,M(,N))))),C(F,G(,I)))";//根据树形图改写成的//二叉树括号表示法的字符串*str//char str[100];scanf("%s",&str);//自行输入括号表示的二叉树CreateBTNode(b,str); //创建树bprintf("\n");printf("输出二叉树:");//输出二叉树bDispBTNode(b);printf("\n");printf("'H'结点:");//找到'H'节点,输出其左右孩子值p=FindNode(b,'H');printf("\n");if (p!=NULL){printf("左孩子节点的值");printf("%c",p->lchild->data);printf("\n");printf("右孩子节点的值");printf("%c",p->rchild->data);printf("\n");//此处输出p的左右孩子节点的值}printf("\n");printf("二叉树b的深度:%d\n",BTNodeHeight(b));//输出b的高度printf("二叉树b的结点个数:%d\n",NodesCount(b));//输出b的节点个数printf("\n");printf(" 先序遍历序列:\n");//输出b的四种遍历顺序printf(" 算法:");PreOrder(b);printf("\n");printf(" 中序遍历序列:\n");printf(" 算法:");InOrder(b);printf("\n");printf(" 后序遍历序列:\n");printf(" 算法:");PostOrder(b);printf("\n");printf(" 层次遍历序列:\n");printf(" 算法:");LevelOrder(b); printf("\n");}四、实验心得与小结通过本次实验,我熟悉二叉树的基本知识内容,对课本的知识有了更加深刻的理解与掌握掌握。

二叉树的定义及基本操作

二叉树的定义及基本操作
五、实验结果及分析
(所输入的数据及相应的运行结果,运行结果要有提示信息,运行结果采用截图 方式给出。)
2
① 输入界面
②输出结果
③测试式子 6*((5+(2+)*8)+3)
六、总结与体会
(调试程序的心得与体会,若实验课上未完成调试,要认真找出错误并分析原因 等。)
每次的实验,总是很受打击。不过,在这过程中,能让我发现自己的 不足,逐渐改善,这是做实验给我最大的收获。 七、程序清单(包含注释)
四、实验记录
(调试过程及调试中遇到的问题及解决办法,其他算法的存在与实践等。) ① 调试过程老是出现访问冲突的错问,通过上网查找访问冲突方面的消息,才
知道应该是指针指错地址,经过调试,最终解决了问题。 ②
调试过程中还出现了这个问题,Status CreateBiTree(BiTree T),当这样定 义时,问题就出现了,但是 Status CreateBiTree(BiTree &T)这样定义就没问题 了,这个想不通。
-
+
/
1.中缀表达式(中序遍历): a+(b*(c-d))-(e/f)
a
*e
2.前缀表达式/波兰式(前序遍历):
f
-+a*b-cd/ef
b-
3.后缀表达式/逆波兰式(后序遍历): abcd-*+ef/-
《《《《《
《 《《《《
C《《《 《 P129
cd
表达式二叉树
1
三、实验所涉及的知识点 递归函数 二叉树
输入说明
***\n"); printf("*** 请按先序输入表达式,当结点的左子树或者右
子树为空时输入‘#‘***\n");
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

实验三二叉树的基本运算
一、实验目的
1、使学生熟练掌握二叉树的逻辑结构和存储结构。

2、熟练掌握二叉树的各种遍历算法。

二、实验内容
题目一:二叉树的基本操作实现(必做题)
[问题描述]
建立一棵二叉树,试编程实现二叉树的如下基本操作:
1. 按先序序列构造一棵二叉链表表示的二叉树T;
2. 对这棵二叉树进行遍历:先序、中序、后序以及层次遍历,分别输出结点的遍历序列;
3. 求二叉树的深度/结点数目/叶结点数目;(选做)
4. 将二叉树每个结点的左右子树交换位置。

(选做)
[基本要求]
从键盘接受输入(先序),以二叉链表作为存储结构,建立二叉树(以先序来建立),
[测试数据]
如输入:ABCффDEфGффFффф(其中ф表示空格字符)
则输出结果为
先序:ABCDEGF
中序:CBEGDFA
后序:CGEFDBA
层序:ABCDEFG
[选作内容]
采用非递归算法实现二叉树遍历。

三、算法设计
1、主要思想:根据二叉树的图形结构创建出二叉树的数据结构,然后
用指针对树进行操作,重点掌握二叉树的结构和性质。

2、本程序包含四个模块:
(1)结构体定义
(2)创建二叉树
(3)对树的几个操作
(4)主函数
四、调试分析
这是一个比较简单程序,调试过程中并没有出现什么问题,思路比较清晰
五、实验结果
六、总结
此次上机实验对二叉树进行了以一次实际操作,让我对二叉树有了更深的了解,对二叉树的特性有了更熟悉的认知,让我知
道了二叉树的重要性和便利性,这对以后的编程有更好的帮助。

七、源程序
#include<iostream>
#include<queue>
using namespace std;
#define TElemType char
#define Status int
#define OK 1
#define ERROR 0
typedef struct BiTNode{
TElemType data;
struct BiTNode * lchild, *rchild;
}BiTNode,* BiTree;
Status CreateBiTree(BiTree &T)
{
TElemType ch;
cin >> ch;
if (ch == '#')
T = NULL;
else
{
if (!(T = (BiTNode *)malloc(sizeof(BiTNode))))
exit(OVERFLOW);
T->data = ch;
CreateBiTree(T->lchild);
CreateBiTree(T->rchild);
}
return OK;
}
Status PreOrderTraverse(BiTree T)
{
if (T)
{
cout << T->data;
if (PreOrderTraverse(T->lchild))
if (PreOrderTraverse(T->rchild))
return OK;
return ERROR;
}
else
return OK;
}
Status InOrderTraverse(BiTree T)
{
if (T)
{
InOrderTraverse(T->lchild);
cout << T->data;
InOrderTraverse(T->rchild);
}
return OK;
}
Status PostOrderTraverse(BiTree T) {
if (T)
{
PostOrderTraverse(T->lchild);
PostOrderTraverse(T->rchild);
cout << T->data;
}
return OK;
}
Status leOrderTraverse(BiTree T)
{
std::queue<BiTree> Q;
if (T == NULL)return ERROR;
else{
Q.push(T);
while (!Q.empty())
{
T = Q.front();
Q.pop();
cout << T->data;
if (T->lchild != NULL)
Q.push(T->lchild);
if (T->rchild != NULL)
Q.push(T->rchild);
}
}
return OK;
}
Status change(BiTree T)
{
BiTree temp = NULL;
if (T->lchild == NULL && T->rchild == NULL) return OK;
else{
temp = T->lchild;
T->lchild = T->rchild;
T->rchild = temp;
}
if (T->lchild)
change(T->lchild);
if (T->rchild)
change(T->rchild);
return OK;
}
int FindTreeDeep(BiTree T){
int deep = 0;
if (T){
int lchilddeep = FindTreeDeep(T->lchild);
int rchilddeep = FindTreeDeep(T->rchild);
deep = lchilddeep >= rchilddeep ? lchilddeep + 1 : rchilddeep + 1;
}
return deep;
}
int main()
{
BiTree T;
CreateBiTree(T);
cout << "先序遍历顺序为:";
PreOrderTraverse(T);
cout << endl;
cout << "中序遍历顺序为:";
InOrderTraverse(T);
cout << endl;
cout << "后序遍历顺序为:";
PostOrderTraverse(T);
cout << endl;
cout << "层序遍历顺序为:";
leOrderTraverse(T);
cout << endl;
cout << "二叉树深度为:" << FindTreeDeep(T)<<endl;
cout << "左右子树交换后:";
change(T);
cout << "先序遍历顺序为:";
PreOrderTraverse(T);
cout << endl;
return 0;
}。

相关文档
最新文档