文件内容格式:
解释:一行中 如 1 2 3 代表1 有左孩子2, 有右孩子3 ;如2 0 4 代表 2 没有左孩子 ,有右孩子4
需要注意的是 :你必须按照顺序来进行书写 也就是说 写了 1 2 3 那你必须先写2 即便2 没有左右孩子 也要写成2 0 0 然后再写3 x x,这样才符合我的代码逻辑
上面文件所创建的二叉树样式如下
创建代码如下:
biTree* createInFile() {//从文件中读取二叉树数据,注:文件数据存储为 每一行 根 左孩子 右孩子
FILE* fp;
int root, lNode, rNode;//三者分别对应文档中一行中的值,即根和左右孩子
biTree* T = (biTree*)malloc(sizeof(biTree));
T->lchild = NULL;
T->rchild = NULL;
Squeue* createQueue(int);
bool isEmpty(Squeue * );
bool enQueue(Squeue*, biTree*, int);
bool isEmpty(Squeue*);
bool deQueue(Squeue*, biTree**, int);
biTree* p = T;//工作指针
Squeue* sq = createQueue(MAXSIZE);
fp = fopen("biTree.txt", "r");//打开文件
int flag = 0;//判断是否是第一次操作
while (3 == fscanf(fp, "%d %d %d", &root, &lNode, &rNode))
{
!flag++ ? p->data = root : deQueue(sq, &p, MAXSIZE);//利用flag,进而判断是否是读取第一行,因为此时队列无数据
biTree* left = (biTree*)malloc(sizeof(biTree));//创建左孩子节点指针
biTree* right = (biTree*)malloc(sizeof(biTree));//创建右孩子节点指针
if (lNode) {//如果值不为零(0代表没有孩子),创建左孩子并赋值
left->data = lNode;
p->lchild = left;//连接孩子
}
else {//否则直接将左孩子置为空
p->lchild = NULL;
}
if (rNode) {//如果值不为零,创建右孩子孩子并赋值
right->data = rNode;
p->rchild = right;
}
else {//否则直接将右孩子置为空
p->rchild = NULL;
}
//把左右孩子入队,方便下次操作
if (p->lchild)enQueue(sq, p->lchild, MAXSIZE);//左孩子入队
if (p->rchild)enQueue(sq, p->rchild, MAXSIZE);//左孩子入队
}
while (!isEmpty(sq)) {//将剩余节点的左右孩子置为空
deQueue(sq, &p, MAXSIZE);//取出队首节点
p->lchild = NULL;
p->rchild = NULL;
}
fclose(fp);
return T;
}
//先序递归遍历
void preOrder(biTree* T) {
if (T != NULL) {
printf("%d ", T->data);
preOrder(T->lchild);
preOrder(T->rchild);
}
}
int main() {
biTree* T;
T = createInFile();
preOrder(T);
return 0;
}
如上,易看出用到了队列这个数据结构,所以想要运行,还需队列相关代码,如下:
/*
此文件用于创建一个顺序队列,出队,入队,判断队空,判断队满等操作
*/
#include <stdio.h>
#include <stdlib.h>
#define TYPE biTree*
//#define TYPE char
//#define TYPE int
struct biTree {
char data;
biTree *lchild;
biTree *rchild;
};
struct Squeue {
TYPE *arr;
int front, rear;
};
//创建队列
Squeue *createQueue(int n) {
Squeue *sq = ( Squeue *)malloc(sizeof( Squeue));
sq->arr = (TYPE *)malloc(sizeof(TYPE)*n);//数组大小
sq->front = 0;
sq->rear = 0;
return sq;
}
//判断队满(这里采用牺牲一个存储单元来实现,约定队头指针在队尾指针的下一个位置作为队满的标志)
bool isFull(Squeue *sq, int maxSize) {
return (sq->rear + 1) % maxSize == sq->front;
}
//判断队空
bool isEmpty(Squeue *sq) {
return sq->front == sq->rear;
}
//判断队列中元素个数
int count(Squeue *sq, int maxSize) {
return (sq->rear - sq->front + maxSize) % maxSize;
}
//入队
bool enQueue(Squeue *sq, TYPE data, int maxSize) {
if (isFull(sq, maxSize)) return false;
sq->arr[sq->rear] = data;
sq->rear = (sq->rear + 1) % maxSize;
return true;
}
//出队
bool deQueue(Squeue *sq, TYPE *data,int maxSize) {
if (isEmpty(sq)) return false;
*data = sq->arr[sq->front];
sq->front = (sq->front + 1) % maxSize;
return true;
}
//打印队列中元素
//void printQ(Squeue *sq,int maxSize) {
// if (isEmpty(sq)) return ;
// int np = sq->front;
// while (np!=sq->rear) {
// printf("%d ",sq->arr[np]);
// np = (np + 1) % maxSize;
// }
//}
如你想要运行,这两个代码文件均需具备
运行结果如下:先序遍历结果