数据结构-堆排序
2016-12-09 15:44
197 查看
堆排序
堆排序下面讨论利用堆进行排序的方法。可以分两种情况分别讨论:
① 如果初始序列是堆,则可通过反复执行如下操作而最终得到一个有序序列:
输出根:即将根(第一个元素)与当前子序列中的最后一个元素交换。
调整堆:将输出根之后的子序列调整为堆(元素个数比输出前少1个)。
向下筛。
② 如果初始序列不是堆,则首先要将其先建成堆,然后再按 ① 的方式来实现。
现在的问题是:如何由一个无序序列建成一个堆?
向上筛。
事实上,由无序序列建堆可通过反复调用筛选操作来实现。
为此,需满足筛选的条件,即左右子树必须为堆。
因此,建堆过程要从下往上逐棵子树地进行筛选。
从易于编程的角度出发,根的下标自然是按从大到小,即根的下标按照从n/2到1的次序将各子树调整为堆。
即:从最后一棵(最右边)高度为2的子树开始调整为堆。从右往左,自底向上(向总树根)逐层调整为堆。
【例】由初始序列(12,15,30,80,100,46,78,33,90,86,64,55,120,230,45)构建堆。
【解】首先由序列构建一棵完全二叉树,自最右高度为2的子树开始,然后从右往左,自底向上逐层调整为堆。
调整过程见后图。
代码块
#define maxlen 100 #define MaxSize 20 typedef int KeyType; //定义关键字类型 typedef char InfoType[10]; typedef struct //记录类型 { KeyType key; //关键字项 InfoType data; //其他数据项,类型为InfoType } RecType; //排序的记录类型定义 class rank { public: rank(); virtual ~rank(); RecType R[MaxSize]; // int data[maxlen]; int high; void shuru(int x); void shuchu(); void sift(RecType R[],int low,int high); void heapsort(RecType R[],int n); void initlist(); }; #endif #include "stdafx.h" #include "rank.h" #include "iostream.h" ////////////////////////////////////////////////////////////////////// // Construction/Destruction ////////////////////////////////////////////////////////////////////// rank::rank() { } rank::~rank() { } void rank::initlist()//录入 { // printf("please input some 数:\n"); int i=1; // R[i]=0; while(EOF!=scanf("%d",&R[i])) //输入数 { i++; if(getchar()=='\n') break; } high= i-1; // printf("data[top]= %d\n",data[top]); } void rank::shuchu() { for (int i=1; i<=high; i++) printf("%d ",R[i]); cout<<endl; } void rank::sift(RecType R[],int low,int high) { int i=low,j=2*i; //R[j]是R[i]的左孩子 RecType temp=R[i]; while (j<=high) { if (j<high && R[j].key<R[j+1].key) //若右孩子较大,把j指向右孩子//j变为2i+1 j++; //左孩子小于右孩子时,左右交换(左孩子要大于右孩子) if (temp.key<R[j].key)//双亲结点小于左孩子时,交换(双亲结点要大于左孩子) { R[i]=R[j]; //将R[j]调整到双亲结点位置上 i=j; //修改i和j值,以便继续向下筛选 j=2*i; } else break; //筛选结束 } R[i]=temp; } void rank::heapsort(RecType R[],int n) { int i; RecType temp; for (i=n/2; i>=1; i--) //循环建立初始堆 sift(R,i,n); //调整堆,形成75 57 48 40 19 34 38 11 6 13 4000 9 7 for (i=n; i>=2; i--) //进行n-1次循环,完成推排序 { temp=R[1]; //将第一个元素同当前区间内R[1]对换 R[1]=R[i]; R[i]=temp; //最大值交换到最后 sift(R,1,i-1); //筛选R[1]结点,得到i-1个结点的堆 //前面的无序区调整为堆 } //调整堆 } #include "stdafx.h" #include "rank.h" #include "iostream.h" int main(int argc, char* argv[]) { rank r; // int x; cout<<"请随意输入一些数字: "; r.initlist(); cout<<"数组长度为: "<<r.high<<endl; cout<<"未排序的结果为: "; r.shuchu(); r.heapsort(r.R,r.high); cout<<"堆排序之后的结果为: "; r.shuchu(); // printf("Hello World!\n"); return 0; }
相关文章推荐
- 数据结构--堆排序
- 【数据结构】算法10.10-10.11 堆排序
- 堆数据结构与堆排序的个人理解
- 数据结构-堆排序
- 数据结构之堆和堆排序
- 【算法与数据结构】图说堆排序
- 数据结构复习之–“堆排序”-JAVA实现
- 数据结构面试之十一——排序2(归并、快速、堆排序)
- 数据结构(6)堆排序
- 数据结构-排序算法详解(插入排序,希尔排序,堆排序,归并排序,快速排序,桶式排序)
- 浅谈算法和数据结构: 五 优先级队列与堆排序
- 【数据结构】堆排序
- 数据结构 JAVA描述(十一) 选择排序(直接选择排序,树形选择排序,堆排序)
- 数据结构之堆排序
- 数据结构实际应用----订单排序(堆排序求前N大)
- 数据结构和算法16 之堆排序
- 数据结构与算法学习笔记——堆排序
- 【数据结构】浅谈算法和数据结构:优先队列和堆排序
- 【数据结构】将一组数据升序排序(利用堆排序)
- java数据结构 堆与堆排序