排序算法——堆排序
2017-05-19 13:46
225 查看
有一点需要注意,那就是,左孩子的下标是2×s+1,右孩子下标是2×s,注意是下标,例如数组1到10,那么下标为13579的全部是左孩子(构造树的时候1第一个数是根,第二个数是左孩子,第三个是右孩子,然后第四个数则是第一个左孩子的左孩子,以此类推)。最大堆:每个父节点都比子节点大;最小堆:每个父节点都比子节点小
[22:42:20] vi t.c [22:42:27] gcc t.c [22:42:28] ./a.out 父节点已经排好: 10 8 9 7 3 4 5 6 1 2 1 2 3 4 5 6 7 8 9 10 [22:42:30] cat t.c #include<stdio.h> void head(int a[],int i,int len) { int p=a[i]; int child=2*i+1;//child 左节点,child+1右节点 while(child<len) { if(child+1<len&&a[child]<a[child+1]) ++child;//如果左节点比右节点小,令child变成右节点下标 if(a[i]<a[child])//父节点与子节点比较,小于就移动 { a[i]=a[child];//父节点赋上子节点的值 i=child;//那么原来的父节点下标就变成子节点的下标 child=2*i+1;//令子节点的下标等于它的左孩子,因为不能只比较一次,需要循环比较,确保每一个子节点都比父节点小 } else break;//父节点比子节点大,直接退出了 a[i]=p;//完成交换 } } void sort(int a[],int len) { int i,t; for(i=(len-1)/2;i>=0;i--)//这里把每个父节点排好,这个循环结束后,每个父节点都比子节点大 head(a,i,len); //下面这个是用来查看父节点是否排好的 printf("父节点已经排好: "); for(i=0;i<len;i++) printf("%d ",a[i]); printf("\n"); for(i=len-1;i>0;--i)//这个循环是用来把堆顶最大那个节点放到相应的字节点位置的,因为用了t变量进行了交换操作,所以这个循环每执行一次,在堆顶的都是最大的值 { t=a[i]; a[i]=a[0]; a[0]=t;//交换 head(a,0,i);//重新调整堆,让它再次成为最大堆 } } int main() { int i; int a[]={3,1,5,7,2,4,9,6,10,8}; int length=sizeof(a)/sizeof(a[0]); sort(a,length); for(i=0;i<length;i++) printf("%d ",a[i]); printf("\n"); return 0; } [22:42:38]
相关文章推荐
- 排序算法-堆排序
- 排序算法之堆排序
- 用Python实现八大排序算法--堆排序
- 排序算法之堆排序(优先队列)
- 【Java常用排序算法】选择排序(简单选择排序、堆排序)
- 排序算法之 堆排序
- 排序算法2--简单选择排序、堆排序
- 其他排序算法:快速、归并、堆排序
- C++编程练习(13)----“排序算法 之 堆排序“
- 几种常见排序算法的实现(冒泡法,选择法,插入法,快速排序、堆排序)
- 深入浅出理解排序算法之-堆排序
- 排序算法——堆排序(java语言描述)
- 常见排序算法的实现(三)——堆排序
- 排序算法之堆排序(js)
- 排序算法——堆排序 (转)
- 排序算法之堆排序(Heapsort)解析
- 排序算法-之选择排序(直接选择排序,堆排序)
- 排序算法(插入排序、shell排序、冒泡排序、选择排序、合并排序、堆排序、快速排序、计数排序、基数排序、桶排序)
- 三种排序算法(归并排序、快速排序,堆排序)
- 排序算法-------堆排序(大根堆)