c++堆排序实现(heapsort) (算法导论)

来源:互联网 发布:汶川地震真实死亡知乎 编辑:程序博客网 时间:2024/05/21 12:29

利用最大堆实现。

最大堆:最大堆性质是除了根结点意外的所有结点 i 都要满足A[parent[i]] >= A[i]

需要利用到的一个性质:当用数组表示存储n个元素的堆时,叶结点的下标分别是n/2, n/2+1, n/2 + 2, ......,n - 1.  (下标从0开始)

需要用到的函数有:

void max_heapify(int *a, int i)    //通过让a[i]的值在最大堆中“逐级下降”,从而使得以下标i为根结点的字数重新遵循最大堆的性质。O(lgn)

void build_max_heap(int *a)            //对树中非叶结点都调用一次max_heapify(a, i)。  O(n)

void heapsort(int *a, int n)        //对长度为n的数组a调用堆排序。  O(nlgn)

//heapsort.cppinline void swap(int &a, int &b) { int t = a; a = b; b = t; }inline int parent(int i) { return (i-1) >> 1; }         //下标都是从0开始,与算导上不一样inline int left(int i) { return (i << 1) + 1; }inline int right(int i) { return (i << 1) + 2; }int heap_size, heap_length;          //heap_length是数组元素个数,heap_size是有多少个元素存储在数组中。0<=heap_size<=heap_lengthvoid max_heapify(int *a, int i) {             //O(lgn), 维护heap的性质,使得以下标i为根结点的子树重新遵循最大堆的性质int l = left(i), r = right(i);int largest = 0;if (l < heap_size && a[l] > a[i])largest = l;elselargest = i;if (r < heap_size && a[r] > a[largest])largest = r;if (largest != i) {swap(a[i], a[largest]);max_heapify(a, largest);}}void build_max_heap(int *a) {             //O(n), 对树中非叶结点都调用一次 max_heapifyheap_size = heap_length;for (int i = heap_length/2 - 1; i >= 0; --i)   //可以证明下标为n/2-1到0的结点为非叶结点max_heapify(a, i);              //i逆序递减的原因:任何时候对结点i调用max_heapify,该i的两个子树都是最大堆}void heapsort(int *a, int n) {           //O(nlgn),调用heapsort(a, n)对数组a排序heap_length = n;build_max_heap(a);for (int i = heap_length - 1; i >= 1; --i) {swap(a[0], a[i]);--heap_size;max_heapify(a, 0);}}


1 0
原创粉丝点击