LeetCode 347. 前 K 個高頻元素【桶排序】

題目描述

給定一個非空的整數數組,返回其中出現頻率前 k 高的元素。

示例 1:

輸入: nums = [1,1,1,2,2,3], k = 2
輸出: [1,2]
示例 2:

輸入: nums = [1], k = 1
輸出: [1]

提示:

  • 你可以假設給定的 k 總是合理的,且 1 ≤ k ≤ 數組中不相同的元素的個數。
  • 你的算法的時間複雜度必須優於 O(n log n) , n 是數組的大小。
  • 題目數據保證答案唯一,換句話說,數組中前 k 個高頻元素的集合是唯一的。
  • 你可以按任意順序返回答案。

解題思路

顧名思義,桶排序的意思是爲每個值設立一個桶,桶內記錄這個值出現的次數(或其它屬 性),然後對桶進行排序。針對樣例來說,我們先通過桶排序得到三個桶[1,2,3,4],它們的值分別 爲[4,2,1,1],表示每個數字出現的次數。

緊接着,我們對桶的頻次進行排序,前k 大個桶即是前k 個頻繁的數。這裏我們可以使用各種 排序算法,甚至可以再進行一次桶排序,把每個舊桶根據頻次放在不同的新桶內。針對樣例來說, 因爲目前最大的頻次是 4,我們建立 [1,2,3,4] 四個新桶,它們分別放入的舊桶爲 [ [3,4],[2],[],[1] ], 表示不同數字出現的頻率。

最後,我們從後往前遍歷,直到找到 k 箇舊桶。

AC

class Solution {
public:
    vector<int> topKFrequent(vector<int>& nums, int k) {
        unordered_map<long,long> mp;
        int max_count=0;
        for(auto x:nums){
            ++mp[x];
            if(max_count<=mp[x]) max_count=mp[x];
        }
        vector<vector<int>> v(max_count+1);
        for(auto it:mp)
            v[it.second].push_back(it.first);
        vector<int> ans;
        for(int i=max_count;i>=0;i--){
            for(auto x:v[i]){
                ans.push_back(x);
                if(ans.size()==k) break;
            }
            if(ans.size()==k) break;
        }
        return ans;
    }
};
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章