LeetCode 347. Top K Frequent Elements
原题链接在这里:https://leetcode.com/problems/top-k-frequent-elements/
题目:
Given a non-empty array of integers, return the k most frequent elements.
For example,
Given [1,1,1,2,2,3]
and k = 2, return [1,2]
.
Note:
- You may assume k is always valid, 1 ≤ k ≤ number of unique elements.
- Your algorithm's time complexity must be better than O(n log n), where n is the array's size.
题解:
先计算出element 和对应的frequency.
然后使用bucket sort. 把element按照出现频率放在bucket中.
因为一共只有n 个元素, 那么最大的频率只能是n. n = nums.length. 所以bucket的大小是n+1, 才能对应最大频率.
然后从bucket后扫到前,因为后面的elements 频率高. 加到res中直到res的size到达k.
Note: bucket的生成等号右边是ArrayList[] 而不能是ArrayList<Integer>[], 因为complier 不能判准加进ArrayList中的type, 只有run time才能知道. 所以这里complier不允许确定type.
Time Complexity: O(n), n = nums.length.
Space: O(n).
AC Java:
1 class Solution { 2 public int[] topKFrequent(int[] nums, int k) { 3 HashMap<Integer, Integer> hm = new HashMap<>(); 4 for(int num : nums){ 5 hm.put(num, hm.getOrDefault(num, 0) + 1); 6 } 7 8 int n = nums.length; 9 ArrayList<Integer>[] buckets = new ArrayList[n + 1]; 10 for(int i = 0; i <= n; i++){ 11 buckets[i] = new ArrayList<Integer>(); 12 } 13 14 for(Map.Entry<Integer, Integer> entry : hm.entrySet()){ 15 buckets[entry.getValue()].add(entry.getKey()); 16 } 17 18 int[] res = new int[k]; 19 int ind = 0; 20 for(int i = n; i >= 0; i--){ 21 for(int num : buckets[i]){ 22 res[ind++] = num; 23 if(ind == k){ 24 return res; 25 } 26 } 27 } 28 29 return res; 30 } 31 }
AC C++:
1 class Solution { 2 public: 3 vector<int> topKFrequent(vector<int>& nums, int k) { 4 vector<int> res; 5 if(nums.size() == 0 || k <= 0){ 6 return res; 7 } 8 9 unordered_map<int, int> map; 10 for(int num : nums){ 11 map[num]++; 12 } 13 14 vector<vector<int>> buckets(nums.size() + 1); 15 for(auto [k, v] : map){ 16 buckets[v].push_back(k); 17 } 18 19 for(int i = buckets.size() - 1; i >= 0; i--){ 20 for(int can : buckets[i]){ 21 res.push_back(can); 22 if(res.size() == k){ 23 return res; 24 } 25 } 26 } 27 28 return res; 29 } 30 };
AC Python:
1 class Solution: 2 def topKFrequent(self, nums: List[int], k: int) -> List[int]: 3 res = [] 4 n = len(nums) 5 map = Counter(nums) 6 buckets = [[] for _ in range(n + 1)] 7 for key, val in map.items(): 8 buckets[val].append(key) 9 10 for i in range(n, -1, -1): 11 for num in buckets[i]: 12 res.append(num) 13 if len(res) == k: 14 return res 15 16 return res
类似Sort Characters By Frequency, Top K Frequent Words, K Closest Points to Origin, Sort Array by Increasing Frequency.