(一)二叉树的创建
二叉树的表现形式有三种:链表、数组、结构数组。
1.链表
#include<stdio.h>
#include<stdlib.h>
typedef char ElementType;
typedef struct BiTree {
ElementType data;
struct BiTree *lChild;
struct BiTree *rChild;
}*BiTree;
void CreateBiTree_1(BiTree *T) {
char ch;
scanf("%c", &ch);
if (ch == '#')
*T = NULL;
else
{
*T = (BiTree)malloc(sizeof(struct BiTree));
(*T)->data = ch;
CreateBiTree(&(*T)->lChild);
CreateBiTree(&(*T)->rChild);
}
}
BiTree CreateBiTree_2() {
char ch;
BiTree T;
scanf("%c", &ch);
if (ch == '#')
T = NULL;
else
{
T = (BiTree)malloc(sizeof(struct BiTree));
T->data = ch;
T->lChild = CreateBiTree();
T->rChild = CreateBiTree();
}
return T;
}
上面是以前序方式创建的二叉树。当然也可以以中序或者后序的方式创建。三种创建方式之间的差别仅仅在于为节点 赋值 的时机不同。事实上,用以上三种方式创建或者遍历二叉树时,创建或者遍历 路线 是一致的。
2. 数组
数组实现方式依赖的是完全二叉树的性质。
3.结构数组
因使用了链表思想将元素存储在数组中,结构数组又被成为静态链表。
#include<stdio.h>
#include<stdlib.h>
#define MAXSIZE 10
#define Null -1
typedef char ElementType;
typedef int Tree;
typedef struct TreeNode {
ElementType data;
Tree left;
Tree right;
}T1[MAXSIZE], T2[MAXSIZE];
Tree CreateBiTree(struct TreeNode T[]) {
int N, root = -1;
scanf("%d", &N);
getchar();
if (N) {
int check[MAXSIZE], i;
char cl, cr;
for (i = 0; i < N; i++) check[i] = 0;
for (i = 0; i < N; i++) {
scanf("%c %c %c", &T[i].data, &cl, &cr);
getchar();
if (cl == '-')
T[i].left = Null;
else
{
T[i].left = cl - '0';
check[T[i].left] = 1;
}
if (cr == '-')
T[i].right = Null;
else
{
T[i].right = cr - '0';
check[T[i].right] = 1;
}
}
for (i = 0; i < N; i++)
if (!check[i]) break;
root = i;
}
return root;
}
(二).二叉树的遍历
1.中序遍历的非递归实现
void InOrderTraverse(BiTree T) {
BiTree BT = T;
Stack s = CreateStack();
while (BT || !IsEmpty(s)) {
while (BT){
Push(s, BT);
BT = BT->lChild;
}
//私以为这个判断是多余的。
//满足最外层while循环意味着BT! = NULL 或者 IsEmpty == False。
//如果满足BT != NULL,肯定有元素被压入栈中;如果满足IsEmpty == false,栈中肯定存在元素。
//也就是说,只要满足最外层的循环条件,此判断一定是多余的。
if (!IsEmpty(s)) {
Pop(s, &BT);
printf("%c ", BT->data);
BT = BT->rChild;
}
}
}
只需改变一下printf语句的位置就能变身为前序遍历。后序遍历有点不同,还没搞清楚怎么做,待更新!
2.层序遍历
void Traverse(BiTree T) {
if (!T) return;
Queue Q = CreateQueue();
Enqueue(T, Q);
ElementType_Queue x = NULL;
while (!IsEmpty(Q)) {
Dequeue(&x, Q);
printf("%c", x->data);
if (x->left) Enqueue(x->left, Q);
if (x->right) Enqueue(x->right, Q);
}
}