二叉树的简介以及ADT实现
2014-09-06 22:28
253 查看
1.树是n个结点的优先集合T,满足一下的性质:
1)有一个被称之为root的结点
2)有其余的结点可以分为m个互不相交的集合T1,T2,T3,,,这些集合本身也是一棵树,每颗子树也有自己的根结点。
2.一些名词介绍
度:树中每个结点具有的子树的数目称为该结点的度
度为0的结点称为叶子或者终端节点。不为0的称之为非终端结点或者分支结点。
结点的子树的根称为该结点的孩子,在(完全)二叉树中,左边的称为左孩子,右边的称为右孩子。相应的,该结点称为孩子的双亲。同一个双亲的孩子互相称为兄弟。
深度:树中结点的最大层次称为书的深度或者高度。
有序树:将树中结点的各子树看成是从左到右的有次序的。
森林:是m棵互不相交的树的集合
3.二叉树的一些性质
性质1:一棵非空二叉树的第i层上最多有2i-1个结点。
证明:利用数学归纳法进行证明。
第一步:当i为1时,成立有1个结点
满足此式
第二步:假设当i=k时,假设此式成立则在第k层上有2k-1个结点
第三步:当i=k+1时,k+1层上结点最多为k层的2倍
则2*2k-1
= 2k
此时满足关系式。
性质2:一棵高度为i的二叉树,最多由2k-1个结点
证明:当结点最多的时候,此时一定为满二叉树,此时结点的计算为:num=20+21+22+23+……+2i-1此时根据等比数列的计算公式可得num=2k-1.
性质3:对于一棵非空二叉树,如果叶子结点数为n0,度数为2的结点数为n2,则有n0
= n2+1成立(最大度数为2)
证明:假设度数为1的结点的数目为n1,
则此时二叉树中所有num = n1 + n1+ n2;
设置分支总数为num1,
num = num1+1,(分支简单说就是连的线的条数),而num1=n1+2*n2,所以
n1+n2+n3 = n1+2*n2+1-------》n0=n2+1成立
性质4:具有n个结点的完全二叉树的深度为[log2N
]+1
证明:假设n个结点的深度为k
则
2k-1 -1 <n <= 2k-1
(前面是k-1层的最多的结点个数后面是k层的最多的结点个数)
性质5:(这个只是简单的介绍下)
如果对一颗有n个结点的完全二叉树的结点按层次序自上而下,每一层自左向右编号,若设置根结点的编号为1,则对任意编号为i的结点有:
1)如果i=1
则为根结点;如果i>1,则其父节点的个数为[i/2] []表示取整
2)如果2*i>n,则编号为i的结点为叶子节点,没有左儿子,否则它的做儿子应该为2*i
3)如果2*i+1>n,则编号为i的结点没有右儿子,否则它的编号为2*i+1;
4.二叉树的ADT实现
#include"stdafx.h"
#include<iostream>
usingnamespacestd;
template<classT>
classbitNode
{
protected:
//这里是防止以后程序出现指针和引用
typedefT*
pT;
typedefT&
rT;
typedefconstT*
const_pT;
typedefconstT&
const_rT;
typedefbitNode<T>*
pNode;
typedefconstbitNode<T>*
const_pNode;
typedefbitNode<T>&
rNode;
typedefconstbitNode<T>&
const_rNode;
public:
Tdata;
pNodelChild,rChild;
public:
bitNode():lChild(NULL),rChild(NULL){};
bitNode(Tval,pNodelchild=NULL,pNoderchild =NULL):data(val),lChild(lchild),rChild(rchild){};
~bitNode(){};
//设置一些set方法
voidsetData(const_rTval) {
data =
val;};
voidsetLeftChild(const_pNodelchild){
lChild =
lchild;};
voidsetRightChild(const_pNoderchild) {
rChild =
rchild;};
//设置一些get方法
TgetData()const {returndata;};
pNodegetLeftChild()
const {returnlChild;};
pNodegetRightChild()
const{returnrChild;};
const_pNodemax(const_pNodeval1,const_pNodeval2)
{
if(val1 >
val2)
returnval1;
else
returnval2;
}
intgetHeight(const_pNodepRoot) //获取深度 方法是在左子树和右子树中寻找最深的层次
{
if(pRoot==NULL) return
0;
else
return 1+max(pRoot->lChild,pRoot->rChild);
}
intgetSize(const_pNodepRoot)
const//获取节点数主要是通过递归
{
if(pRoot ==
NULL) return 0;
else
return 1+getSize(pRoot->lChild)+getSize(pRoot->rChild);
}
/*
在此三种遍历方式略去下次在使用呵呵
*/
};
template<classT>
classbitTree
{
public:
typedefbitNode<T>
Node;
typedefbitNode<T>*
pNode;
typedefconstbitNode<T>&
const_rNode;
typedefconstT*
const_pT;
typedefconstT&
const_rT;
typedefconstbitTree<T>*
const_pTree;
typedefconstbitTree<T>&
const_rTree;
private:
pNoderoot;
voiddelAllNode(pNodepRoot) //使用递归删除
{
if(pRoot!=NULL)
{
delAllNode(pRoot->lChild);
delAllNode(pRoot->rChild);
deletepRoot;
}
}
public:
bitTree():root(NULL){}
bitTree(const_rTval)
{
root =
newNode(val);
}
~bitTree(){delAllNode(root);}
//释放所有的结点
boolisEmpty()
const{return (root==NULL)};
pNodegetRoot()
const{returnroot; }; //
};
//简单设置下根结点和输出 大家可以随意扩展 数据结构书籍上还有删除一个特定的结点(注意:带子树删除)
//在一个位置插入节点等等
int_tmain(intargc,
_TCHAR*
argv[])
{
bitTree<int>
pTree(1);
cout<<pTree.getRoot()->getData()<<endl;
getchar();
return 0;
}
1)有一个被称之为root的结点
2)有其余的结点可以分为m个互不相交的集合T1,T2,T3,,,这些集合本身也是一棵树,每颗子树也有自己的根结点。
2.一些名词介绍
度:树中每个结点具有的子树的数目称为该结点的度
度为0的结点称为叶子或者终端节点。不为0的称之为非终端结点或者分支结点。
结点的子树的根称为该结点的孩子,在(完全)二叉树中,左边的称为左孩子,右边的称为右孩子。相应的,该结点称为孩子的双亲。同一个双亲的孩子互相称为兄弟。
深度:树中结点的最大层次称为书的深度或者高度。
有序树:将树中结点的各子树看成是从左到右的有次序的。
森林:是m棵互不相交的树的集合
3.二叉树的一些性质
性质1:一棵非空二叉树的第i层上最多有2i-1个结点。
证明:利用数学归纳法进行证明。
第一步:当i为1时,成立有1个结点
满足此式
第二步:假设当i=k时,假设此式成立则在第k层上有2k-1个结点
第三步:当i=k+1时,k+1层上结点最多为k层的2倍
则2*2k-1
= 2k
此时满足关系式。
性质2:一棵高度为i的二叉树,最多由2k-1个结点
证明:当结点最多的时候,此时一定为满二叉树,此时结点的计算为:num=20+21+22+23+……+2i-1此时根据等比数列的计算公式可得num=2k-1.
性质3:对于一棵非空二叉树,如果叶子结点数为n0,度数为2的结点数为n2,则有n0
= n2+1成立(最大度数为2)
证明:假设度数为1的结点的数目为n1,
则此时二叉树中所有num = n1 + n1+ n2;
设置分支总数为num1,
num = num1+1,(分支简单说就是连的线的条数),而num1=n1+2*n2,所以
n1+n2+n3 = n1+2*n2+1-------》n0=n2+1成立
性质4:具有n个结点的完全二叉树的深度为[log2N
]+1
证明:假设n个结点的深度为k
则
2k-1 -1 <n <= 2k-1
(前面是k-1层的最多的结点个数后面是k层的最多的结点个数)
性质5:(这个只是简单的介绍下)
如果对一颗有n个结点的完全二叉树的结点按层次序自上而下,每一层自左向右编号,若设置根结点的编号为1,则对任意编号为i的结点有:
1)如果i=1
则为根结点;如果i>1,则其父节点的个数为[i/2] []表示取整
2)如果2*i>n,则编号为i的结点为叶子节点,没有左儿子,否则它的做儿子应该为2*i
3)如果2*i+1>n,则编号为i的结点没有右儿子,否则它的编号为2*i+1;
4.二叉树的ADT实现
#include"stdafx.h"
#include<iostream>
usingnamespacestd;
template<classT>
classbitNode
{
protected:
//这里是防止以后程序出现指针和引用
typedefT*
pT;
typedefT&
rT;
typedefconstT*
const_pT;
typedefconstT&
const_rT;
typedefbitNode<T>*
pNode;
typedefconstbitNode<T>*
const_pNode;
typedefbitNode<T>&
rNode;
typedefconstbitNode<T>&
const_rNode;
public:
Tdata;
pNodelChild,rChild;
public:
bitNode():lChild(NULL),rChild(NULL){};
bitNode(Tval,pNodelchild=NULL,pNoderchild =NULL):data(val),lChild(lchild),rChild(rchild){};
~bitNode(){};
//设置一些set方法
voidsetData(const_rTval) {
data =
val;};
voidsetLeftChild(const_pNodelchild){
lChild =
lchild;};
voidsetRightChild(const_pNoderchild) {
rChild =
rchild;};
//设置一些get方法
TgetData()const {returndata;};
pNodegetLeftChild()
const {returnlChild;};
pNodegetRightChild()
const{returnrChild;};
const_pNodemax(const_pNodeval1,const_pNodeval2)
{
if(val1 >
val2)
returnval1;
else
returnval2;
}
intgetHeight(const_pNodepRoot) //获取深度 方法是在左子树和右子树中寻找最深的层次
{
if(pRoot==NULL) return
0;
else
return 1+max(pRoot->lChild,pRoot->rChild);
}
intgetSize(const_pNodepRoot)
const//获取节点数主要是通过递归
{
if(pRoot ==
NULL) return 0;
else
return 1+getSize(pRoot->lChild)+getSize(pRoot->rChild);
}
/*
在此三种遍历方式略去下次在使用呵呵
*/
};
template<classT>
classbitTree
{
public:
typedefbitNode<T>
Node;
typedefbitNode<T>*
pNode;
typedefconstbitNode<T>&
const_rNode;
typedefconstT*
const_pT;
typedefconstT&
const_rT;
typedefconstbitTree<T>*
const_pTree;
typedefconstbitTree<T>&
const_rTree;
private:
pNoderoot;
voiddelAllNode(pNodepRoot) //使用递归删除
{
if(pRoot!=NULL)
{
delAllNode(pRoot->lChild);
delAllNode(pRoot->rChild);
deletepRoot;
}
}
public:
bitTree():root(NULL){}
bitTree(const_rTval)
{
root =
newNode(val);
}
~bitTree(){delAllNode(root);}
//释放所有的结点
boolisEmpty()
const{return (root==NULL)};
pNodegetRoot()
const{returnroot; }; //
};
//简单设置下根结点和输出 大家可以随意扩展 数据结构书籍上还有删除一个特定的结点(注意:带子树删除)
//在一个位置插入节点等等
int_tmain(intargc,
_TCHAR*
argv[])
{
bitTree<int>
pTree(1);
cout<<pTree.getRoot()->getData()<<endl;
getchar();
return 0;
}
相关文章推荐
- Mashups简介以及简单实现分析
- 将节点作为模板参数的二叉树的设计,以及常用二叉树算法(求公共祖先等)的实现
- 判断完全二叉树以及求二叉树深度的递归与非递归算法实现
- 二叉树的建立、节点查找以及节点删除C和C++实现
- 【转】二叉树的实现及操作以及指针使用和删除注意事项
- MD5加密简介以及C#下的操作实现
- 二叉树的建立以及三种遍历方式的递归、非递归的实现
- [置顶] 二叉树的非递归前序、中序以及后序遍历C++模版类实现
- [置顶] 二叉树的建立、节点查找以及节点删除C和C++实现
- [置顶] ffmpg简介以及用它实现音频视频合并(java)
- 二叉树创建、前序遍历、中序遍历、后序遍历 的 递归与非递归实现 以及 层次遍历
- 实现二叉树以及链表发现的问题
- 实现二叉树以及链表发现的问题
- 二叉树的非递归前序、中序以及后序遍历C++模版类实现
- 二叉树的创建,先序、中序、后序遍历的递归实现以及层序遍历
- C#实现二叉树数据结构以及先序、中序、后续遍历
- C++ 二叉树的实现以及指针使用注意事项
- MD5加密简介以及C#下的操作实现
- 安装、进程-云计算学习笔记---hadoop的简介,以及安装,用命令实现对hdfs系统进行文件的上传下载-by小雨
- 二叉树的建立以及前序、中序、后序遍历的递归和非递归实现