#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; }