栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

堆排序与TopK问题c++源码

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

堆排序与TopK问题c++源码

#include
using namespace std;
#include

//调整数组v以i位置为根的子树为小根堆,数组堆的范围0到k-1
void HeadAdjustDown(vector& v, int i, int k);
//对前k个元素建立小根堆
void BuildMinHeap(vector& v, int k);
//取最小k个数
void GetLeastNumbers_Solution(vector& input, int k);

//调整数组v以i位置为根的子树为大根堆,数组堆的范围0到k-1
void HeadAdjustUp(vector& v, int i, int k);
//对前k个元素建立大根堆
void BuildMaxHeap(vector& v, int k);
//取最大k个数
void GetMostNumbers_Solution(vector& input, int k);

//堆排序从小到大
void MinHeapSort(vector& v);
//堆排序从大到小
void MaxHeapSort(vector& v);


int main() {
    vector v;
    v.push_back(53);
    v.push_back(17);
    v.push_back(78);
    v.push_back(9);
    v.push_back(45);
    v.push_back(65);
    v.push_back(87);
    v.push_back(32);

    int k = 8;
    
    cout << "这是原始数组:";
    for (auto& a : v) {
        cout << a << " ";
    }
    cout << endl;

    GetLeastNumbers_Solution(v,5);
    GetMostNumbers_Solution(v,5);

    MaxHeapSort(v);
    MinHeapSort(v);

    return 0;
}

//调整数组v以i位置为根的子树为小根堆,数组堆的范围0到k-1
void HeadAdjustDown(vector& v, int i, int k) {
    int tmp = v[i];
    //调整v[i]节点为根的子树,v[i]的左右孩子为v[2i+1]和v[2i+2]
    for (int j = 2 * i + 1; j < k; j = 2 * j + 1) {
        if (j + 1 < k && v[j] > v[j + 1]) {
            //在右孩子存在的情况下
            //左孩子小,j就已经指向左孩子
            //右孩子小,那么让j指向右孩子,也就是j++
            j++;
        }
        if (tmp < v[j])
            break;//根节点本来就比左右孩子小
        else {
            v[i] = v[j]; //左右孩子中最小的数往上提
            i = j; //让i指向它的左右孩子中最小的
        }
    }
    v[i] = tmp;
}

//对前k个元素建立小根堆
void BuildMinHeap(vector& v,int k) {
    //前k个数下标0到k-1  最后一个非叶子节点下标是(k - 1)/2      
    for (int i = (k - 1) / 2; i >= 0; i--) {
        //从最后一个非叶子节点开始逐个调整建立小根堆
        HeadAdjustDown(v, i, k);
    }
}

//取最小k个数 
void GetLeastNumbers_Solution(vector& input, int k) {
    BuildMaxHeap(input, k);
    for (int i = k; i < input.size(); i++) {
        if (input[i] >= input[0])
            continue;
        else {
            int tmp = input[0];
            input[0] = input[i];
            input[i] = tmp;

            HeadAdjustUp(input, 0, k);
        }
    }
    vector v;
    for (int i = 0; i < k; i++) {
        v.push_back(input[i]);
    }
    cout << "数组最小k个数:";
    for (auto& a : v) {
        cout << a << " ";
    }
    cout << endl;
}

//调整数组v以i位置为根的子树为大根堆,数组堆的范围0到k-1
void HeadAdjustUp(vector& v, int i, int k) {
    int tmp = v[i];
    //调整v[i]节点为根的子树,v[i]的左右孩子为v[2i+1]和v[2i+2]
    for (int j = 2 * i + 1; j < k; j = 2 * j + 1) {
        if (j + 1 < k && v[j + 1] > v[j]) {
            j++;
        }
        if (tmp > v[j])
            break;
        else {
            v[i] = v[j];
            i = j;
        }
    }
    v[i] = tmp;
}

//对前k个元素建立大根堆
void BuildMaxHeap(vector& v, int k) {
    //前k个数下标0到k-1  最后一个非叶子节点下标是(k - 1)/2      
    for (int i = (k - 1) / 2; i >= 0; i--) {
        //从最后一个非叶子节点开始逐个调整建立小根堆
        HeadAdjustUp(v, i, k);
    }
}

//取最大k个数
void GetMostNumbers_Solution(vector& input, int k) {
    BuildMinHeap(input, k);
    for (int i = k; i < input.size(); i++) {
        if (input[i] <= input[0])
            continue;
        else {
            int tmp = input[0];
            input[0] = input[i];
            input[i] = tmp;
    
            HeadAdjustDown(input, 0, k);
        }
    }
    vector v;
    for (int i = 0; i < k; i++) {
        v.push_back(input[i]);
    }
    cout << "数组最大k个数:";
    for (auto& a : v) {
        cout << a << " ";
    }
    cout << endl;
}

//堆排序从小到大
void MinHeapSort(vector& v) {
    int len = v.size();
    while (len) {
        BuildMaxHeap(v, len);
        swap(v[0], v[len-1]);
        len--;
    }
    cout << "堆排序从小到大:";
    for (auto& a : v) {
        cout << a << " ";
    }
    cout << endl;
    
}
//堆排序从大到小
void MaxHeapSort(vector& v) {
    int len = v.size();
    while (len) {
        BuildMinHeap(v, len);
        swap(v[0], v[len-1]);
        len--;
    }
    cout << "堆排序从大到小:";
    for (auto& a : v) {
        cout << a << " ";
    }
    cout << endl;    
}

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/913757.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号