C语言实现,100个整数构造平衡二叉树,以树的形式输出

#include <stdlib.h>
#include <stdio.h> 
#define NUM 100
int a[100];
typedef struct node {
	int value;
	int bf;
	struct node* left;
	struct node* right;
}NODE, *NODEP;
NODEP adjust(NODEP p);
/*将100个整数随机打乱*/
void init()
{
    int i, j, k, n;
    for(i=0;i < 100;i++)
        a[i] = i;
    srand((int)time(0));
    for(i = 0;i < 100;i++){
        j = rand()%100;
        k = rand()%100;
         
        n = a[j];
        a[j] = a[k];
        a[k] = n;
    }
}
/*输出1被打乱的100个整数*/
void output()
{
    int i;
    for(i =0;i < NUM;i++) 
                 printf(((i+1)%10 == 0)?"%5d\n":"%5d", a[i]);
	putchar('\n');
}
/*取得节点的深度*/
int get_deep(NODEP p)
{
	int l, r, max;
	if (p == NULL)
		return 0;
	l = get_deep(p->left);
	r = get_deep(p->right);
	max = (l >=r)?l:r;
	return 1+max;
}
/*设置节点的bf(平衡因子)位,再调整树满足平衡二叉树*/
NODEP set_bf(NODEP p)
{
     	int l, r;
	if (p == NULL)
		return NULL;
	p->left = set_bf(p->left);
	p->right = set_bf(p->right);
	
	l = get_deep(p->left);
	r = get_deep(p->right);
	p->bf = l-r;
	p->left = set_bf(p->left);
	p->right = set_bf(p->right);
	if ((p->bf ==2)||(p->bf == -2)) {
                p = adjust(p);
                return p;
        }
	return p;
}
/*在平衡二叉树中插入节点*/
void insert(NODEP p, int i)
{
	NODEP q;
	if (p->value < i) {
		if(p->right == NULL) {
			q = (NODEP)malloc(sizeof(NODE));
			q->value = i;
			q->bf = 0;
			q->left = NULL;
			q->right = NULL;
			p->right = q;
		}
		else
			insert(p->right, i);
	}
	if (p->value > i) {
		if (p->left == NULL) {
			q= (NODEP)malloc(sizeof(NODE));
			q->value = i;
			q->bf = 0;
			q->left = NULL;
			q->right = NULL;
			p->left = q;
		}
		else
			insert(p->left, i);
	}
}
/*调整插入节点后的树,使其仍满足平衡二叉树特性*/
NODEP adjust(NODEP p)
{
	NODEP n, m;
	
	if (p->bf == 2) {
		n = p->left;
		/*LL*/
		if (n->bf == 1) {
			p->left = n->right;
			n->right = p;
			return n;
		}
		/*LR*/
		else {
			m = n->right;
			n->right = m->left;
			m->left = n;
			p->left = m->right;
			m->right = p;
			return m;
		}
	}
	if (p->bf == -2) {
		n = p->right;
		/*RR*/
		if (n->bf == -1) {
			p->right = n->left;
			n->left = p;
			return n;
		}
		/*RL*/
		else {
			m = n->left;
			n->left = m->right;
			m->right = n;
			p->right = m->left;
			m->left= p;
			return m;
	
		}
	}
}
void output1(NODEP root);
/*构建平衡二叉树*/
NODEP insert_all()
{
	int i;
	NODEP root;
        root = (NODEP)malloc(sizeof(NODE));
        root->left = NULL;
        root->right = NULL;
	for(i = 0,root->value = a[i++];i < NUM;i++) {
		insert(root, a[i]);
		root = set_bf(root);
	}
	return root;
}
/*以树的结构输出*/
void output1(NODEP root)
{
	if (root == NULL) 
		return;
	
	printf("%d", root->value);
	putchar('(');
	output1(root->left);
	putchar(',');
	output1(root->right);
	putchar(')');
	
}
int  main()
{
    	init();
	output();
	NODEP root;
	root = insert_all();
	output1(root);
	return 1;
}

输出:

71   96   84    3   82    5    0   75    8   89

   10   15   12   16   14   51   66    4   87   26

   20   76   97   23   24   31   63   85   22   93

   78   38   35   33   34   56   73   88   50   47

   42   59   40   94   57   45   41    7   72   37

    2   18    1   74   54   55   32   79   46   70

   60   99   80   83   64   44   62    6   48   29

   52   11   36   19   58   90   17   77   30   68

   43   67   65   27   49   92   39   53    9   13

   25   28   91   21   81   69   98   61   86   95


47(26(8(5(3(1(0(,),2(,)),4(,)),7(6(,),)),15(12(10(9(,),11(,)),14(13(,),)),20(18(16(,17(,)),19(,)),23(22(21(,),),24(,25(,)))))),35(31(29(27(,28(,)),30(,)),33(32(,),34(,))),40(37(36(,),38(,39(,))),44(42(41(,),43(,)),45(,46(,)))))),71(56(51(49(48(,),50(,)),54(52(,53(,)),55(,))),63(59(57(,58(,)),61(60(,),62(,))),66(64(,65(,)),68(67(,),70(69(,),))))),84(76(73(72(,),75(74(,),)),79(78(77(,),),82(80(,81(,)),83(,)))),93(89(87(85(,86(,)),88(,)),91(90(,),92(,))),96(94(,95(,)),98(97(,),99(,)))))))

总结:1、一直没找到一个办法以树的结构输出书,那样看起来更直观,目前就是一个“()”代表一对二叉树,代表一层。

          2、对于二叉排序树,采用中序输出,正好是由小到大

          3、在递归程序中,改变程序先后顺序,可决定是从内层向外层执行,还是层外层向内层执行

后续:用树的结构形象地输出树。

          1、算法应该是在脑袋中有一定思想再去编程,而不是在编程过程中尝试

#include <stdlib.h>
#include <stdio.h> 
/*50个整数输出更容易观察,超过50就会换行,所以设置50*/
#define NUM 50
int a[100];
typedef struct node {
	int value;
	int bf;
	struct node* left;
	struct node* right;
}NODE, *NODEP;
NODEP adjust(NODEP p);
void init()
{
    int i, j, k, n;
    for(i=0;i < 100;i++)
        a[i] = i;
    srand((int)time(0));
    for(i = 0;i < 100;i++){
        j = rand()%100;
        k = rand()%100;
         
        n = a[j];
        a[j] = a[k];
        a[k] = n;
    }
}
void output()
{
    int i;
    for(i =0;i < NUM;i++) 
                 printf(((i+1)%10 == 0)?"%5d\n":"%5d", a[i]);
	putchar('\n');
}
int get_deep(NODEP p)
{
	int l, r, max;
	if (p == NULL)
		return 0;
	l = get_deep(p->left);
	r = get_deep(p->right);
	max = (l >=r)?l:r;
	return 1+max;
}
NODEP set_bf(NODEP p)
{
     	int l, r;
	if (p == NULL)
		return NULL;
	p->left = set_bf(p->left);
	p->right = set_bf(p->right);
	
	l = get_deep(p->left);
	r = get_deep(p->right);
	p->bf = l-r;
	p->left = set_bf(p->left);
	p->right = set_bf(p->right);
	if ((p->bf ==2)||(p->bf == -2)) {
                p = adjust(p);
                return p;
        }
	return p;
}

void insert(NODEP p, int i)
{
	NODEP q;
	if (p->value < i) {
		if(p->right == NULL) {
			q = (NODEP)malloc(sizeof(NODE));
			q->value = i;
			q->bf = 0;
			q->left = NULL;
			q->right = NULL;
			p->right = q;
		}
		else
			insert(p->right, i);
	}
	if (p->value > i) {
		if (p->left == NULL) {
			q= (NODEP)malloc(sizeof(NODE));
			q->value = i;
			q->bf = 0;
			q->left = NULL;
			q->right = NULL;
			p->left = q;
		}
		else
			insert(p->left, i);
	}
}
NODEP adjust(NODEP p)
{
	NODEP n, m;
	
	if (p->bf == 2) {
		n = p->left;
		if (n->bf == 1) {
			p->left = n->right;
			n->right = p;
			return n;
		}
		else {
			m = n->right;
			n->right = m->left;
			m->left = n;
			p->left = m->right;
			m->right = p;
			return m;
		}
	}
	if (p->bf == -2) {
		n = p->right;
		if (n->bf == -1) {
			p->right = n->left;
			n->left = p;
			return n;
		}
		else {
			m = n->left;
			n->left = m->right;
			m->right = n;
			p->right = m->left;
			m->left= p;
			return m;
	
		}
	}
}
void output1(NODEP root);
NODEP insert_all()
{
	int i;
	NODEP root;
        root = (NODEP)malloc(sizeof(NODE));
        root->left = NULL;
        root->right = NULL;
	for(i = 0,root->value = a[i++];i < NUM;i++) {
		insert(root, a[i]);
		root = set_bf(root);
	}
	return root;
}
void output1(NODEP root)
{
	if (root == NULL) 
		return;
	
	printf("%d", root->value);
	putchar('(');
	output1(root->left);
	putchar(',');
	output1(root->right);
	putchar(')');
	
}
/*构造另外一棵树,树分为deep层,该树为一个矩阵,left指向下(为下一层),right指向右(为一层),每一层为之前树中每一层的元素,下一层为之前树中下一层的元素*/
NODEP get_output(NODEP root, NODEP head, int n, int deep)
{
	int m = n;
	NODEP head_next = head;
	NODEP p;

		while(m--)
			head_next = head_next->left;
		while(head_next->right != NULL)
			head_next = head_next->right;
		p = (NODEP)malloc(sizeof(NODE));
                head_next->right = p;
                p->right = NULL;
                p->left = NULL;
		if (root == NULL)
			p->value = 100;
		else 
			p->value = root->value;
		++n;
	if (n < deep) {
	        /*如果树不为空,则将左右子孩子传入*/
		if (root != NULL) {
			head = get_output(root->left, head, n, deep);
                	head = get_output(root->right, head, n, deep);
		}
		/*如果树为空,为了保持新树的结构,继续向其中传入空值*/
		else {
			head = get_output(root, head, n, deep);
			head = get_output(root, head, n, deep);
		}
	}
	return head;	
}
int  main()
{
    	int deep, i, j, k;
	init();
	output();
	NODEP root, head, p, q;

	
	root = insert_all();
	output1(root);
	deep = get_deep1(root);
	printf("\n%d\n", deep);
	
	for (i = 0,head = (NODEP)malloc(sizeof(NODE)), head->left = NULL, head->right = NULL , p = head;i < (deep - 1);i++) {
		q = (NODEP)malloc(sizeof(NODE));
		q->right = NULL;
		q->left = NULL;
		p->left = q;
		p = q;
	}
	head = get_output(root, head, 0, deep);
	for (p = head, i = deep;p != NULL;p = p->left, i--, putchar('\n')) {
		j = i-1;
		k = 1;
		while(j--)
			k *= 2;
		k--;
		while(k--)
			printf("  ");
		for(q = p->right;q != NULL;q = q->right) {
		        /*空节点输出NO*/
			printf((q->value == 100)?"NO":"%2d", q->value);
		j = i;
		k = 1;
		while(j--)
			k*=2;
		k--;
		while(k--)
			printf("  ");
		}
	}
	return 1;
}

C语言实现,100个整数构造平衡二叉树,以树的形式输出_第1张图片







你可能感兴趣的:(C语言实现,100个整数构造平衡二叉树,以树的形式输出)