堆排序
利用堆的结构(事实上就是二叉树)进行排序,首先对数据进行调整调整为一个大根堆或者小根堆,其次取出最大或最小的值放入最后一个页节点,继续调整剩余的二叉树形成一个新的堆。递归直到完毕。当中有几个概念须要明确,对于一个有n个节点的全然二叉树第一个非页节点为(n/2-1),其左子树为 当前节点下标(i*2+1)。
详细实现例如以下
void stuckSmall(long *str,int start,int end){ if(end<=0 || start>=end || str == NULL) return; int left = 2*start+1; int right = left+1; int max = start; if(start<=end){ if(right<=end && str[max]<str[right]) max = right; if(left<=end && str[max]<str[left]) max = left; if(max != start){ swap(&str[start],&str[max]); //对子树进行递归调整 stuckSmall(str,max,end); } } } void stuckSort(long *str,int length){ if(str == NULL || length<=0) return; int i=0; //最后一个非叶节点 int n = length/2-1; //将数组调整为堆结构,最后一个非叶节点处開始 for(n;n>=0;n--){ stuckSmall(str,n,length); } for(i=length-1;i>=0;i--){ //将堆中的第一个值放入最后的位置 swap(&str[0],&str[i]); //将剩余调整为小根堆 stuckSmall(str,0,i-1); } }完整代码
#include <stdio.h> #include <malloc.h> void swap(long *A,long *B){ long tmp; tmp = *A; *A = *B; *B = tmp; } int genrand(int num,long * array ){ if (num>10000) return 0 ; srand((unsigned int)time(0)); int i=0; for(i=0;i<num;i++) array[i] = rand(); return 1; } void stuckSmall(long *str,int start,int end){ if(end<=0 || start>=end || str == NULL) return; int left = 2*start+1; int right = left+1; int max = start; if(start<=end){ if(right<=end && str[max]<str[right]) max = right; if(left<=end && str[max]<str[left]) max = left; if(max != start){ swap(&str[start],&str[max]); stuckSmall(str,max,end); } } } void stuckSort(long *str,int length){ if(str == NULL || length<=0) return; int i=0; int n = length/2-1; for(n;n>=0;n--){ stuckSmall(str,n,length); } for(i=length-1;i>=0;i--){ swap(&str[0],&str[i]); stuckSmall(str,0,i-1); } } void call(){ long *array = (long *)malloc(sizeof(long)*10); genrand(10,array); stuckSort(array,10); int i=0; for(i;i<10;i++) printf("%ld ",array[i]); } void main(int argc,char **argv){ call(); }
执行环境:ubuntu14.04、gcc