Leetcode347:前K个高频元素~~后续快速排序再看看~ 主要涉及到最小堆优先队列的pair--以及哈希表的索引之auto xx=map.begin()

在这里插入图片描述

思路: 这个题目相当于用了最小堆的优先队列,但是我们以往优先队列只能传1个元素。在这里我们传送了pair~~而且我们pair的比较对象在second中,所以我们要创建一个自己的比较程序。cmp 注意到这个cmp函数的return意味着,m是新来的或者后面的 n是前面的,新来的如果大 那就交换,也就是return是true的时候就交换 往前面交换,也就是从大到小。
注意到最小堆应该是从小到达排序,应该是小于号,但是注意到这边就是反的 !!!

class Solution {
public:
    static bool cmp(pair<int, int>& m, pair<int, int>& n) {
        return m.second > n.second;
    }

    vector<int> topKFrequent(vector<int>& nums, int k) {
        unordered_map<int, int> occurrences;
        for (auto& v : nums) {
            occurrences[v]++;
        }

        // pair 的第一个元素代表数组的值,第二个元素代表了该值出现的次数
        priority_queue<pair<int, int>, vector<pair<int, int>>, decltype(&cmp)> q(cmp);
        for (auto& [num, count] : occurrences) {
            if (q.size() == k) {
                if (q.top().second < count) {
                    q.pop();
                    q.emplace(num, count);
                }
            } else {
                q.emplace(num, count);
            }
        }
        vector<int> ret;
        while (!q.empty()) {
            ret.emplace_back(q.top().first);
            q.pop();
        }
        return ret;
    }
};

第二种算法很巧妙,对哈希表的运用要比较熟练,有时候取哈希表元素都要用auto,其实在这里我们可以用哈希表的.begin() 等来表示哈希表中某一个最先地址的元素,虽然我不知道他是什么,但是肯定是某个元素~~ 每次取哈希表中的一个元素,和其他元素比值大小,保留最大的,每次选出当前排名最好的。然后从哈希表中抹除这个元素。继续排名K次。遍历哈希表每个元素的方式为了和for类似,这里采用了.begin()和 .end();

class Solution {
public:
    vector<int> topKFrequent(vector<int>& nums, int k) {
        unordered_map<int,int> mp;
        for(int i=0;i<nums.size();i++){
            mp[nums[i]]++;
        }
        vector<int> ret;
        for(int i=0;i<k;i++){
            auto its=mp.begin();
            for(auto it=mp.begin();it!=mp.end();it++){
                if(its->second < it->second){
                    its=it;
                }
            }
            ret.push_back(its->first);
            mp.erase(its);
        }
      return ret;
    }
};

另外,还有一种方法是快速排序,详情看Leetcode解答,当复习到集中排序的方法时再回顾把!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值