堆排序

在最大堆中,最大堆性质是指除了根以外的所有结点i都满足:
A[PARENT(i)]>=A[i]
在最小堆中,最小堆性质是指除了根以外的所有结点i都满足:
A[PARENT(i)]<=A[i]

维护堆的性质
void maxheap(vector<int> &heap,int i,int heapsize)
该函数用于维护最大堆性质的重要过程。这里假定根结点为LEFT(i)和RIGHT(i)的二叉树都是最大堆。思路:通过将heap[i]的值在最大堆中“逐级下降”。

//堆元素的序号习惯从1开始,这样方便计算双亲结点和孩子结点序号
void maxheap(vector<int> &heap,int i,int heapsize) {
    int left = i * 2;
    int right = i * 2 + 1;
    int large;
    if (left<=heapsize&&heap[left-1] > heap[i-1])
        large = left;
    else large = i;
    if (right<=heapsize&&heap[right-1] > heap[large-1])
        large = right;
    //根结点的值比孩子结点的小,交换后接着往下维护最大堆
    if (large != i) {
        swap(heap[i-1], heap[large-1]);
        maxheap(heap, large, heapsize);
    }
    return;
}

建堆
可以用自底向上的方法利用过程maxheap把一个大小为n=heap.size()的数组转换为最大堆。子数组heap[n/2+1..n]的元素都是树的叶子结点。而叶子结点就可以看作只有一个结点的最大堆。

void buildmaxheap(vector<int> &heap) {
    int length = heap.size();
    //从最后那个非叶子结点开始调整最大堆
    for (int i = length / 2; i > 0; i--) {
        maxheap(heap, i,heap.size());
    }
}

堆排序算法
堆排序算法利用buildmaxheap将输入数组heap[1..n]建成最大堆。数组中的最大元素总在根结点heap[0]中,现将heap[0]与heap[heap.size()-1]交换。然后再利用buildmaxheap将数组heap[1..n-1]建成最大堆。以此类推,最后数组需要建成最大堆的只有一个元素时,排序完成。

void heapSort(vector<int> &heap) {
    buildmaxheap(heap);
    int n = heap.size() - 1;
    int heapsize = heap.size();
    while (n > 0) {
        swap(heap[0], heap[n]);
        heapsize--;
        maxheap(heap, 1, heapsize);
        n--;
    }
}

优先队列
优先队列的一些基本操作。

//返回队列最大值
int maximumheap(vector<int> &heap) {
    return heap[0];
}
//去掉并返回heap的最大值
int extractmaxheap(vector<int> &heap) {
    int heapsize = heap.size();
    int max = heap[0];
    //swap(heap[0], heap[heapsize-1]);
    //直接去掉最大值元素,因此不用交换值
    heap[0] = heap[heapsize - 1];
    heapsize -= 1;
    maxheap(heap, 1, heapsize);
    heap.erase(heap.end() - 1);
    return max;
}
//将第x个元素的关键值增加到key
void increasekeyheap(vector<int> &heap, int x, int key) {
    //key值一定不能小于第x个元素
    if (key < heap[x - 1]) return;
    heap[x - 1] = key;
    int i = x;
    //不断与其父结点的关键值进行比较,如果比父结点的关键值大则交换关键值
    while (i > 1 && heap[i / 2] < heap[i])
    {
        swap(heap[i / 2], heap[i]);
        i = i / 2;
    }
    return;
}
//插入关键值为key的结点
void insert(vector<int> &heap, int key) {
    //先增加一位数组
    heap.push_back(key);
    increasekeyheap(heap, heap.size(), key);
    return;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值