归并排序+快排+快速选择+桶排序

https://www.bilibili.com/video/BV1Pt4y197VZ/?spm_id_from=333.788.recommend_more_video.-1
归并排序入口
在这里插入图片描述
归并排序(递归划分后合并)
在这里插入图片描述
排序具体算法
在这里插入图片描述
快速排序(第一次排完,再利用递归对左右两半排序)

void quick_sort(vector<int> &nums, int l, int r) {
    
    
if (l + 1 >= r) {
    
    
return;
}
int first = l, last = r - 1, key = nums[first];
while (first < last){
    
    
while(first < last && nums[last] >= key) {
    
    
--last;
}
nums[first] = nums[last];
while (first < last && nums[first] <= key) {
    
    
++first;
}
nums[last] = nums[first];
}
nums[first] = key;
quick_sort(nums, l, first);
quick_sort(nums, first + 1, r);
}

快速选择
一般用于求第k大小的数
在这里插入图片描述
第一次排完之后中间下标跟k做对比,决定排哪边

// 主函数
int findKthLargest(vector<int>& nums, int k) {
    
    
int l = 0, r = nums.size() - 1, target = nums.size() - k;
while (l < r) {
    
    
int mid = quickSelection(nums, l, r);
if (mid == target) {
    
    
return nums[mid];
}
if (mid < target) {
    
    
l = mid + 1;
} else {
    
    
r = mid - 1;
} }
return nums[l];
}
// 辅函数 - 快速选择
int quickSelection(vector<int>& nums, int l, int r) {
    
    
int i = l + 1, j = r;
while (true) {
    
    
while (i < r && nums[i] <= nums[l]) {
    
    
++i;
}
while (l < j && nums[j] >= nums[l]) {
    
    
--j;
}
if (i >= j) {
    
    
break; }
swap(nums[i], nums[j]);
}
swap(nums[l], nums[j]);
return j;
}

桶排序
顾名思义,桶排序的意思是为每个值设立一个桶,桶内记录这个值出现的次数(或其它属性),然后对桶进行排序。针对样例来说,我们先通过桶排序得到三个桶 [1,2,3,4],它们的值分别为 [4,2,1,1],表示每个数字出现的次数。
紧接着,我们对桶的频次进行排序,前 k 大个桶即是前 k 个频繁的数。这里我们可以使用各种排序算法,甚至可以再进行一次桶排序,把每个旧桶根据频次放在不同的新桶内。针对样例来说,因为目前最大的频次是 4,我们建立 [1,2,3,4] 四个新桶,它们分别放入的旧桶为 [[3,4],[2],[],[1]],表示不同数字出现的频率。最后,我们从后往前遍历,直到找到 k 个旧桶。
给定一个数组,求前 k 个最频繁的数字。
1.先使用哈希表统计数组中每个数字频率
2.统计完成后,创建一个数组,之前计算的频率作为数组的下标
3.对于出现频率不同的数字集合,存进对应的数组下标

vector<int> topKFrequent(vector<int>& nums, int k) {
    
    
unordered_map<int, int> counts;
int max_count = 0;
for (const int & num : nums) {
    
    
max_count = max(max_count, ++counts[num]);
}
vector<vector<int>> buckets(max_count + 1);
for (const auto & p : counts) {
    
    
buckets[p.second].push_back(p.first);
}
vector<int> ans;
for (int i = max_count; i >= 0 && ans.size() < k; --i) {
    
    
for (const int & num : buckets[i]) {
    
    
ans.push_back(num);
if (ans.size() == k) {
    
    
break; } } }
return ans;
}

おすすめ

転載: blog.csdn.net/qq_45598881/article/details/121188473