1. 程式人生 > >二叉樹的陣列儲存及運算

二叉樹的陣列儲存及運算

二叉樹的陣列儲存

當用陣列儲存完全二叉樹時可以用節點的編號作為陣列下標
當用陣列儲存非完全二叉樹時也可以用節點的編號作為陣列下標,但是要補全節點序列.(用虛擬節點)

2017/8/30 更新
父子節點的位置運算:
陣列0下標不使用
父節點i的左子節點在位置(2*i);
父節點i的右子節點在位置(2*i+1);
子節點i的父節點在位置(i/2);

完整程式碼如下:

//this is tree node size
#define SIZE 20

//求深度
//完全二叉樹的最大節點數量s = (2^n)-1,n = 樹的高度
//對於一個數組結構的tree,要先求tree的深度n,求最大指數2^n-1=size = 2^n = size+1 。所以 n =  log2 (size+1)。n向上取整
int getHeight2(int size){ return (int)ceil(log10((double)size+1)/log10(2.0)); } //求左孩子 int *getLchild(int arr[],int index){ if(index*2 > SIZE){ //printf("this node is not lift child"); return NULL; } return &arr[index*2]; } //求右孩子 int *getRchild(int arr[],int index){ if
(index*2+1 > SIZE){ // printf("this node is not right child"); return NULL; } return &arr[index*2+1]; } //求雙親 int *getParent(int arr[],int index){ if(index < 2 || index > SIZE){ printf("this node is not parent"); return NULL; } return &arr[index/2
]; } //先序遍歷 void perorder2(int *arr, int len){ printf("%d ",arr[len]); if(getLchild(arr,len) != NULL) perorder2(arr,*getLchild(arr,len)); if(getRchild(arr,len) != NULL) perorder2(arr,*getRchild(arr,len)); } //列印空格 void printCH(int k){ char *ch = " "; while(k){ printf("%s",ch); k--; } } //print tree //列印tree,這樣有直觀的感受,按層列印 void printTerr(int arr[]){ int tall = getHeight2(SIZE);//樹的高度,層數 int count = 0,length = 1, i;//換行計數 int k;//元素間距 //k 的值用於控制tree node 間距,當從root節點向下列印時, k是遞減的,k的遞減規律是: n = (n+1) - 2^n ;(n 是當前層數,n-1表示上一層,root的層數n = 數的高度,n從葉子(最末端)向根節點計數.2^n == 1<<n) k = (1 << (tall+1)) - 1; k = k - (1 << tall); for(i = 1; i <= SIZE; i++){ printCH(k);//列印空格方法 printf("%d",arr[i]);//列印元素,每個元素前後要列印空格. printCH(k); count++; //判斷是否列印空格,調整層數 if(count == length){ printf("\n\n"); count = 0; length *=2; tall--; k = k - (1 << tall); } } printf("\n"); } //test tree for array void treeArrsTest(){ int treeArr[] = {NULL,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20}; //先把tree打印出來,這樣比較直觀一點 printTerr(treeArr); printf("\n"); perorder2(treeArr, 1); printf("\n"); printf(" node 5 left child is : %d\n",*getLchild(treeArr,5)); printf(" node 5 right child is 6 : %d\n",*getRchild(treeArr,5)); printf(" node 5 parent is : %d\n",*getParent(treeArr,5)); }