系列文章目录
- leetcode - 双指针问题_leetcode双指针题目-优快云博客
- leetcode - 滑动窗口问题集_leetcode 滑动窗口-优快云博客
- 高效掌握二分查找:从基础到进阶-优快云博客
- leetcode - 前缀和_前缀和的题目-优快云博客
- 动态规划 - 斐波那契数列模型-优快云博客
- 位运算 #常见位运算总结 #题解-优快云博客
- 模拟 - #介绍 #题解-优快云博客
目录
前言
路漫漫其修远兮,吾将上下而求索;
大家可以先自己尝试做一下~
215. 数组中的第K个最大元素 - 力扣(LeetCode)
LCR 159. 库存管理 III - 力扣(LeetCode)
一、分治思想
分治,即分而治之;
将大问题拆解为相同或者相似的子问题,然后在这个子问题额基础上继续进行划分,直到划分到某一个位置为止(该子问题可以快速解决);
其中,排序之中,快排、归并排序就是典型的分治思想;
二、快排
想要更加详细地了解快排可以参考:数据结构与算法 - 快速排序 #hoare版本 #挖坑法 #lomuto前后指针 #三数取中 #三路划分 #introsort自省排序_lomuto法-优快云博客
当待排序列中有大量重复数据的时候,三路划分的思想类似于hoare 版本和lomuto 前后指针的结合;其核心思想是将数组中的数据划分为三段:小于基准值的数据、等于基准值的数据、大于基准值的数据,故而叫做三路划分算法;

数据结构与算法 - 快速排序 #hoare版本 #挖坑法 #lomuto前后指针 #三数取中 #三路划分 #introsort自省排序_lomuto法-优快云博客
当待排序列中有大量重复数据的时候,三路划分的思想类似于hoare 版本和lomuto 前后指针的结合;其核心思想是将数组中的数据划分为三段:小于基准值的数据、等于基准值的数据、大于基准值的数据,故而叫做三路划分算法;
使用三指针:left 、cur、 right
让left 指向等于key 区间的左下标,让right 指向等于 key区间的右下标;然后让cur 遍历整个数组;
三路划分版快排代码如下:
#include<iostream>
#include<algorithm>
#include<string>
#include<vector>
using namespace std;
//三路划分快排
void QuickSort(vector<int>& a, int left, int right)
{
//确保范围合法
if (left >= right) return;
//提前保存一下范围
int begin = left, end = right;
//随机值取基准值
int keyi = left + rand() % (right - left + 1);
swap(a[keyi], a[left]);
keyi = left;
int key = a[left];//基准值
int cur = left + 1;
while(cur <= right)
{
if (a[cur] < key)
{
swap(a[left], a[cur]);
cur++;
left++;
}
else if (a[cur] > key)
{
swap(a[right], a[cur]);
//因为不知道a[right] 中数据地大小,所以right--,而 cur 不动
right--;
}
else//与 key 相等
{
cur++;
}
}
//[begin,left-1] 小于key 的区间
//[left , right] 等于key 的区间
//[right ,end] 大于key 的区间
//继续递归
QuickSort(a, begin, left - 1);
QuickSort(a, right+1, end);
}
int main()
{
//设置随机种子
srand((unsigned int)time(NULL));
vector<int> nums = { 10,2,90,8,76,23,12,11,5,3,2 };
QuickSort(nums, 0, nums.size() - 1);
for (auto e : nums)
{
cout << e << " ";
}
cout << endl;
return 0;
}


最低0.47元/天 解锁文章
1456

被折叠的 条评论
为什么被折叠?



