分治思想求解的问题,但是比较特殊,只有分解问题和求解小问题,不需要合并

每次也只需要经过判断,分解一半,所以比其他分解两边的效率高

最坏情况时间复杂度为O(n^2),期望时间复杂度为O(n)

找基准值时候可以考虑随机选择

#include<iostream>
#include<vector>
#include<algorithm>
#include<random>
#include<ctime>
using namespace std;
int select(vector<int>& data, int left, int right, int k); int main()
{
//次序选择问题:求数组中第k小的元素
// 思想:分而治之
// 将问题分解partition
// 如果要找的第k个元素正好是基准值,那正好,也就是最好情况了,时间复杂度为O(n),因为只进行了一次partition
//如果要找的第k个元素在基准值左侧,也就是左子数组里,那么在子数组里,还是找第k小元素
//如果要找的第k个元素在基准值右侧,也就是右子数组里,那么在右子数组里,找的是第k-(q-p+1)个元素 int k = 1;
vector<int> data = { 7,5,6,4,3,1,9 };
//获取序列元素个数
int length = data.size();
int left = 0;
int right = 6;
int result;//用来保存第k小元素的值
result = select(data, left, right, k);
cout << result << endl;
}
int select(vector<int>& data, int left, int right, int k)
{
if (left == right)
return data.at(left);//递归结束的条件 //这部分是partition,也可以单独写成一个函数调用
int key = data.at(right);
/*这里有一种优化的方法,就是这个中轴数随机的找,然后交换到末尾,再往下执行*/
/*
default_random_engine e(time(0)); //时间引擎
uniform_int_distribution<signed> u(left, right);
int key = u(e);
int tem = data.at(key);
data.at(key) = data.at(right);
data.at(right) = tem;
int ave = data.at(right);
*/
int i = left - 1;
for (int j = left; j < right; j++)
{
if (data.at(j) <= key)
{
i++;
int temp = data.at(j);
data.at(j) = data.at(i);
data.at(i) = temp;
}
}
//将基准值放在合适的位置
i++;
int temp = data.at(i);
data.at(i) = key;
data.at(right) = temp;
//此时的i就是基准值的位置
//以上是partition部分,可以单独写成函数调用 //当前第cur小的元素,这里很重要,一定要这么写
int cur = i - left + 1;
if (k == cur)//如果基准值正好是第k小元素
return data.at(i);
else if (k < cur)//要找的第k小元素出现在左边
{
return select(data, left, i - 1, k);
}
else
{
return select(data, i + 1, right, k - cur);//如果出现在右边,原始的第k小元素在右边子数组中就是第k-cur小元素,这里很重要
}
}

【C++】数组中的第k个最小元素的更多相关文章

  1. 代码题(3)— 最小的k个数、数组中的第K个最大元素、前K个高频元素

    1.题目:输入n个整数,找出其中最小的K个数. 例如输入4,5,1,6,2,7,3,8这8个数字,则最小的4个数字是1,2,3,4. 快排思路(掌握): class Solution { public ...

  2. 寻找数组中的第K大的元素,多种解法以及分析

    遇到了一个很简单而有意思的问题,可以看出不同的算法策略对这个问题求解的优化过程.问题:寻找数组中的第K大的元素. 最简单的想法是直接进行排序,算法复杂度是O(N*logN).这么做很明显比较低效率,因 ...

  3. LeetCode:数组中的第K个最大元素【215】

    LeetCode:数组中的第K个最大元素[215] 题目描述 在未排序的数组中找到第 k 个最大的元素.请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素. 示例 1: ...

  4. Leetcode题目215.数组中的第K个最大元素(中等)

    题目描述: 在未排序的数组中找到第 k 个最大的元素.请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素. 示例 1: 输入: [3,2,1,5,6,4] 和 k = 2 ...

  5. Java实现 LeetCode 215. 数组中的第K个最大元素

    215. 数组中的第K个最大元素 在未排序的数组中找到第 k 个最大的元素.请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素. 示例 1: 输入: [3,2,1,5,6 ...

  6. 215. 数组中的第K个最大元素 + 快速排序 + 大根堆

    215. 数组中的第K个最大元素 LeetCode-215 另一道类似的第k大元素问题:https://www.cnblogs.com/GarrettWale/p/14386862.html 题目详情 ...

  7. LeetCode215. 数组中的第K个最大元素

    215. 数组中的第K个最大元素 问题描述 在未排序的数组中找到第 k 个最大的元素.请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素. 示例 示例 1: 输入: [3 ...

  8. LeetCode 215——数组中的第 K 个最大元素

    1. 题目 在未排序的数组中找到第 k 个最大的元素.请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素. 示例 1: 输入: [3,2,1,5,6,4] 和 k = 2 ...

  9. Leetcode 215.数组中的第k个最大元素

    数组中的第k个最大元素 在未排序的数组中找到第 k 个最大的元素.请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素. 示例 1: 输入: [3,2,1,5,6,4] 和 ...

随机推荐

  1. centos7安装ifconfig

    1,找出哪个包提供了ifconfig命令 yum provides ifconfig 2,通过输出,发现是net-tools提供了ifconfig命令 yum install net-tools

  2. Kerberos与票据的爱情故事

    0x01.Kerberos认证原理 Kerberos是一种认证机制.目的是通过密钥系统为客户端/服务器应用程序提供强大的可信任的第三方认证服务: 保护服务器防止错误的用户使用,同时保护它的用户使用正确 ...

  3. 【Deeplearning】(转)深度学习知识网络

    转自深度学习知识框架,小象牛逼! 图片来自小象学院公开课,下面直接解释几条线 神经网络 线性回归 (+ 非线性激励) → 神经网络 有线性映射关系的数据,找到映射关系,非常简单,只能描述简单的映射关系 ...

  4. 使用Guava RateLimiter限流入门到深入

    前言 在开发高并发系统时有三把利器用来保护系统:缓存.降级和限流 缓存: 缓存的目的是提升系统访问速度和增大系统处理容量 降级: 降级是当服务出现问题或者影响到核心流程时,需要暂时屏蔽掉,待高峰或者问 ...

  5. 【转】Key Presses

    FROM:http://lazyfoo.net/tutorials/SDL/04_key_presses/index.php Key Presses Last Updated 6/11/19 Xing ...

  6. 4g工业路由器的覆盖范围分析

    4G工业路由器通常覆盖范围在60-80米之间,而影响4G工业路由器的覆盖范围有以下几个因素. 影响4g工业路由器覆盖范围的因素一:环境 空旷的环境下4g工业路由器的信号覆盖范围必然更加广阔,如果传输环 ...

  7. 循序渐进VUE+Element 前端应用开发(26)--- 各种界面组件的使用(2)

    在我们使用Vue+Element开发前端的时候,往往涉及到很多界面组件的使用,其中很多直接采用Element官方的案例即可,有些则是在这个基础上封装更好利用.更少代码的组件:另外有些则是直接采用第三方 ...

  8. git使用心得体会

    序言:身为软件工程的学生却一直没有接触Git,实在有些羞愧.得益于孟宁老师的课程,让我对Git有了初步的认识.同样借由此次机会正式接触Git这款程序员必备工具. 参考文献:https://mp.wei ...

  9. P6064 [USACO05JAN]Naptime G

    最近做了多少道 usaco 了,连 FJ 都认识我了呀 题意描述 传送门 给你 \(N\) 段时间其中 \(B\) 段时间你要用来睡眠,再给你每个时间睡眠可获得的效用值 \(U_i\). 可惜的是你每 ...

  10. C++语言学习之STL 的组成

    STL有三大核心部分:容器(Container).算法(Algorithms).迭代器(Iterator),容器适配器(container adaptor),函数对象(functor),除此之外还有S ...