算法导论 二叉树 按层打印

前一篇博客记录了二叉树的中序遍历,打印出来是一个升序的排列。
本篇文章介绍按层遍历打印二叉树,关键是如何换层(何时打印回车符)。
使用sumup和sumdown记录当前行的个数和下一行的个数,
当当前行的元素个数0,打印回车,并且将下一行sumdown赋给sumup,sumdown归零重新计数,这样迭代下去。
如有疑问,欢迎留言。
----------------------------------------------------------------------------------------------------------------------------------------------------------

----------------------------------------------------------------------------------------------------------------------------------------------------------

#include<stdio.h>
#include<malloc.h>
#define N 100
#define K 100
typedef struct link S_L;
typedef struct queue SQ;//队列
struct link {
    int n;
    S_L* left;
    S_L* right;

};//申明二叉树元素的结构体,
struct queue{
S_L array[N];
S_L* head;
S_L* tail;
};//申明队列结构体
int enqueue(SQ* p, S_L n);//入队
S_L *dequeue(SQ* p);//出队
void tree(S_L* p, int n);//二叉树的根
int tree_link(S_L* p, int n);//二叉树递归
int printf_tree_layer(S_L*p);//按层遍历打印二叉树
void happen_rand(int* p, int n);//生成随机数
SQ Q = { {0},&Q.array[0],&Q.array[0] };//Q队列初始化
int n, k = 0, tmp[N+1] = { 0 };
int main()
{
    int array[N] = {0}, i;
    happen_rand(array,N);
    S_L P = {0};
    for (i = 0; i < N; i++) {//二叉树插入元素
        tree(&P, array[i]);
    }
    printf_tree_layer(&P);
    return 0;
}

void tree(S_L* p, int n) {
    if (p->n == 0) {
        p->n = n;
        p->left = NULL;
        p->right = NULL;
    }
    else
        tree_link(p, n);


}

int tree_link(S_L* p, int n) {

    if (n < p->n && p->left == NULL) {
        p->left = (S_L*)malloc(sizeof(S_L));
        p->left->n = n;
        p->left->left = NULL;
        p->left->right = NULL;
        return 0;
    }
    else if (n >= p->n && p->right == NULL) {
        p->right = (S_L*)malloc(sizeof(S_L));
        p->right->n = n;
        p->right->left = NULL;
        p->right->right = NULL;
        return 0;
    }
    else if (n < p->n)
        tree_link(p->left,n);
    else if (n >= p->n)
        tree_link(p->right, n);


}

void happen_rand(int* p, int n){
    int i;
    for (i = 0; i < N; i++) {
        p[i] = rand() % K;

    }
}

int  enqueue(SQ* p, S_L n) {
    *p->tail = n;
    p->tail++;
    if (p->tail == &p->array[N]) {
        p->tail = &p->array[0];
    }//尾部循环
    if (p->head == p->tail)//判断溢出
        return -1;

}

S_L* dequeue(SQ* p) {
    if (p->head == &p->array[N]) {
        p->head = &p->array[0];
    }//尾部循环
    if (p->head == p->tail) //判断溢出
    {  S_L *p=NULL;
        return p;}
    return (p->head++);
}
int sumup=1;//当前行的元素个数
int sumdown=0;//下一行的元素个数
int printf_tree_layer(S_L*p){
    if(0==sumup){//这里是关键,当前元素是0的时候换行,
        if(sumdown==0) return;//判断下一行是否为0
    printf("\n");
        sumup=sumdown;
        sumdown=0;
    }
 printf("%d ",p->n);
    sumup--;//每次打印后当前元素个数减一
 if(NULL!=p->left){ enqueue(&Q,*p->left);sumdown++;}//每次生成子元素后下一行元素个数加一
 if(NULL!=p->right){enqueue(&Q,*p->right);sumdown++;}//每次生成子元素后下一行元素个数加一
    printf_tree_layer(dequeue(&Q));
 
 
}

算法导论 文章被收录于专栏

以小白的角度诠释算法导论,假如有人看不懂,我就面壁思过。

全部评论

相关推荐

10-30 23:23
已编辑
中山大学 Web前端
去B座二楼砸水泥地:这无论是个人素质还是专业素质都👇拉满了吧
点赞 评论 收藏
分享
评论
1
1
分享
牛客网
牛客企业服务