二叉树
来源:互联网 发布:php use function 编辑:程序博客网 时间:2024/05/16 14:44
二叉树是一种树型结构,二叉树的特点是每个节点最多可以有两棵子树。并且,二叉树的两棵子树有左右之分,其次序不能颠倒。二叉树有下面三条性质:
性质1:在二叉树的第i层上最多可以有2^(i-1)个节点。
性质2:深度为k的二叉树最多可以有2^k-1个节点。
性质3:对于一棵二叉树,如果叶子节点数为m,度为2的节点数为n,那么m = n + 1。
下面这个图描述了一棵简单的二叉树。
由于二叉树中每个节点可以有两个子节点,因此二叉树不是一种线性结构。为了方便起见,通常用链式结构表示二叉树中的节点。二叉树中的节点可以用下面的数据结构定义:
typedef struct bitnode { int data; struct bitnode *lchild; struct bitnode *rchild;}bitnode, *bitree;
二叉树遍历是二叉树中的基本操作,按照节点访问顺序不同,可以分为四种方式:
先序遍历: (1)访问根节点;(2)先序遍历左子树;(3)先序遍历又子树。
中序遍历: (1)中序遍历左子树;(2)访问根节点;(3)中序遍历又子树。
后续遍历: (1)后续遍历左子树;(2)后续遍历又子树;(3)访问根节点。
层次遍历: 按照节点在二叉树中的层次从上到下从左到右访问各个节点。
上面这个例子中,各种遍历方式的结果如下:
先序遍历: 5, 8, 12, 1, 6, 9, 20, 11, 17
中序遍历: 12, 8, 6, 1, 9, 5, 11, 17, 20
后续遍历: 12, 6, 9, 1, 8, 17, 11, 20, 5
层次遍历: 5, 8, 20, 12, 1, 11, 6, 9, 17
在对二叉树进行遍历前,我们首先需要先构造一棵二叉树,二叉树可以采用递归方法进行构造,方法如下:
void createbitree(bitnode **t){ int ch; scanf("%d", &ch); if (ch == 0) *t = NULL; else { *t = (bitree)malloc(sizeof(bitnode)); if (*t == NULL) return; (*t)->data = ch; createbitree(&((*t)->lchild)); createbitree(&((*t)->rchild)); } return;}
按照程序设计方法不同,二叉树遍历又可以分为递归算法和非递归算法两种。递归算法比较简单,逻辑非常清晰,代码如下:
// 先序遍历递归算法void preorder(bitree t, void (*visit)(bitree node)){ if (t) { visit(t); preorder(t->lchild, visit); preorder(t->rchild, visit); }}// 中序遍历递归算法void inorder(bitree t, void (*visit)(bitree node)){ if (t) { inorder(t->lchild, visit); visit(t); inorder(t->rchild, visit); }}// 后续遍历递归算法void postorder(bitree t, void (*visit)(bitree node)){ if (t) { postorder(t->lchild, visit); postorder(t->rchild, visit); visit(t); }}
与递归算法相比,非递归算法的逻辑有些复杂,非递归算法借助堆栈实现了二叉树的遍历过程。理解非递归算法的关键是理解各个节点入栈、出栈的顺序。
先序遍历非递归算法
void preordernorec(bitree t, void (*visit)(bitree node)){ bitree queue[100]; bitree p; int index = 0; if (t != NULL) { queue[index++] = t; while (index != 0) { p = queue[--index]; visit(p); if (p->rchild != NULL) { queue[index++] = p->rchild; } if (p->lchild != NULL) { queue[index++] = p->lchild; } } }}
中序遍历非递归算法
void inordernorec(bitree t, void (*visit)(bitree node)){ bitree queue[100]; bitree p; int index = 0; while ((t!= NULL) ||(index != 0)) { if (t != NULL) { queue[index++] = t; t = t->lchild; } else { p = queue[--index]; visit(p); t = p->rchild; } }}
后续遍历非递归算法
void postordernorec(bitree t, void (*visit)(bitree node)){ bitree queue1[100]; bitree queue2[100]; bitree p; int index1 = 0; int index2 = 0; if (t != NULL) { queue1[index1++] = t; while (index1 != 0) { p = queue1[--index1]; queue2[index2++] = p; if (p->lchild != NULL) queue1[index1++] = p->lchild; if (p->rchild != NULL) queue1[index1++] = p->rchild; } for (index1 = index2 - 1; index1 >=0; index1--) visit(queue2[index1]); }}
层次遍历二叉树
void levelorder(bitree t, void (*visit)(bitree node)){ bitree queue[100]; bitree p; int front = 0; int rear = 0; if (t != NULL) { queue[rear++] = t; while (front != rear) { p = queue[front++]; visit(p); if (p->lchild != NULL) queue[rear++] = p->lchild; if (p->rchild != NULL) queue[rear++] = p->rchild; } }}
测试程序
void visit(bitree node){ printf("%d ", node->data);}int main(int argc, char *argv[]){ bitree t; createbitree(&t); printf("pre order: "); preorder(t, visit); printf("\npre order no rec: "); preordernorec(t, visit); printf("\n\nin order: "); inorder(t, visit); printf("\nin order no rec: "); inordernorec(t, visit); printf("\n\npost order: "); postorder(t, visit); printf("\npost order no rec: "); postordernorec(t, visit); printf("\n\nlevel order: "); levelorder(t, visit); printf("\n"); return 0;}输出结果如下:
pre order: 5 8 12 1 6 9 20 11 17
pre order no rec: 5 8 12 1 6 9 20 11 17
in order: 12 8 6 1 9 5 11 17 20
in order no rec: 12 8 6 1 9 5 11 17 20
post order: 12 6 9 1 8 17 11 20 5
post order no rec: 12 6 9 1 8 17 11 20 5
level order: 5 8 20 12 1 11 6 9 17
- 二叉树、二叉堆
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 二叉树
- 面试题33:把数组排成最小的数
- java 刷屏器
- 正则表达式
- Java web登录验证过滤器
- 网页排重算法(转)
- 二叉树
- linux内核中串口驱动注册过程(tty驱动)
- CentOS内核编译make menuconfig出错解决
- 读博之历史
- SQL中使用WITH AS提高性能-使用公用表表达式(CTE)简化嵌套SQL
- xml文件下载到本地—XmlPullParser解析下载到本地的xml(vlc)
- 人才的价值在于贡献度?
- hdu 1226 BFS
- 无法序列化类型 system threading tasks task