1.暴力排序,新建节点类重载小于符号排序。

class Solution {
public:
struct comb{
int index,distance;
comb():index(0),distance(0){}
comb(int a,int b){
index=a;distance=b;
}
bool operator<(const comb& x){
return distance<x.distance;
}
};
vector<vector<int>> kClosest(vector<vector<int>>& points, int K) {
if(points.size()<=K){
return points;
}
vector<comb> vec(points.size());
for(int i=0;i<points.size();++i){
vec[i]=comb(i,points[i][0]*points[i][0]+points[i][1]*points[i][1]);
}
sort(vec.begin(),vec.end());
vector<vector<int>> res(K);
for(int i=0;i<K;++i){
res[i]=points[vec[i].index];
}
return res;
}
};

其实我是想只对索引数组进行排序的,但sort的重载小于符函数不大好写,因为要用到points数组,没法加到函数参数里,所以就先这样写

2.快排划分。想到没必要全排序,因为只需要前k个。若当前划分好的小于K个,到右边再找。若等于K个或者K-1个,则输出。否则到左边缩小划分继续找,O(N logN)时间(大概是这个,具体不会算)。

class Solution {
public:
vector<vector<int>> kClosest(vector<vector<int>>& points, int K)
{
int siz = points.size();
if(K==siz)
{
return points;
}
vector<int> indexes(siz);
for (int i = 0; i < siz; ++i)
{
indexes[i] = i; //存索引
}
vector<vector<int>> res;
quicksort(indexes, points, 0, siz - 1, K, res);
return res;
}
void quicksort(vector<int>& indexes, vector<vector<int>>& points, int le, int ri, const int& K, vector<vector<int>>& res)
{
if (res.size() or le > ri)
{
return;
}
int mi = partition(indexes, points, le, ri, K);
if (mi == K - 1)
{
res.resize(K);
for (int i = 0; i < K; ++i)
{
res[i] = points[indexes[i]];
}
return;
}
else if (mi < K - 1) //目前找到最小的mi+1个,但mi+1<k,所以还要到右半边找k-mi+1个
{
quicksort(indexes, points, mi + 1, ri, K, res);
}
else //mi>k-1,则mi+1>k,左半边元素大于K个
{
quicksort(indexes, points, le, mi - 1, K, res);
}
}
int partition(vector<int>& indexes, vector<vector<int>>& points, int le, int ri, const int& K)
{
if(le==ri)
{
return le;
}
int p = le + rand() % (ri - le + 1);
int temp = indexes[p];
indexes[p] = indexes[ri];
indexes[ri] = temp;
int i = le - 1, j = le;
while (j < ri)
{
if (check(indexes[j], indexes[ri], points)) //索引j对应的点离原点比基准点近
{
int temp = indexes[j];
indexes[j] = indexes[++i];
indexes[i] = temp; //i先+1,再交换i、j处的索引值
}
++j;
}
temp = indexes[i + 1];
indexes[i + 1] = indexes[ri];
indexes[ri] = temp;
return i + 1; //返回基准数位置
}
bool check(int i, int j, vector<vector<int>>& points) //i、j为points的索引
{
if (abs(points[i][0]) < abs(points[j][0]) and abs(points[i][1]) < abs(points[j][1]))
{
return true;
}
return pow(points[i][0], 2) + pow(points[i][1], 2) < pow(points[j][0], 2) + pow(points[j][1], 2);
}
};

3.堆排。考虑到要求的前k个元素并不要求有序,故考虑建长度K的大顶堆,将所有点依次加入直到堆满。之后若当前元素比堆顶还大,丢弃该元素不用。最后留下来的K个就是最小的K个。这K个不是完全有序的,但确实是最小的K个。O(N logK)时间。

class Solution {
public:
static bool cmp(const vector<int>& a, vector<int>& b) {
return a[0] * a[0] + a[1] * a[1] < b[0] * b[0] + b[1] * b[1];
};
vector<vector<int>> kClosest(vector<vector<int>>& points, int K) {
if (K >= points.size()) {
return points;
}
vector<vector<int>>res;
make_heap(res.begin(),res.end(),cmp); //大顶堆
for (auto& point : points) {
if (res.size() >= K) {
if(cmp(point,res[0])){ //当前point小于堆顶,pop堆顶,push当前point
pop_heap(res.begin(), res.end(),cmp);
res.pop_back();
res.push_back(point);
push_heap(res.begin(), res.end(), cmp);
}
}
else{
res.push_back(point);
push_heap(res.begin(), res.end(), cmp);
}
}
return res;
}
};

我看题解好像还有个神仙O(N)解法,没看,估计看了面试也背不出来,就这样。。2019年11月5日 15:23:24

973. 最接近原点的 K 个点的更多相关文章

  1. LeetCode——973. 最接近原点的 K 个点

    我们有一个由平面上的点组成的列表 points.需要从中找出 K 个距离原点 (0, 0) 最近的点. (这里,平面上两点之间的距离是欧几里德距离.) 你可以按任何顺序返回答案.除了点坐标的顺序之外, ...

  2. 【力扣】973. 最接近原点的 K 个点

    我们有一个由平面上的点组成的列表 points.需要从中找出 K 个距离原点 (0, 0) 最近的点. (这里,平面上两点之间的距离是欧几里德距离.) 你可以按任何顺序返回答案.除了点坐标的顺序之外, ...

  3. leetcode-973最接近原点的K个点

    leetcode-973最接近原点的K个点 题意 我们有一个由平面上的点组成的列表 points.需要从中找出 K 个距离原点 (0, 0) 最近的点. (这里,平面上两点之间的距离是欧几里德距离.) ...

  4. [Swift]LeetCode973. 最接近原点的 K 个点 | K Closest Points to Origin

    We have a list of points on the plane.  Find the K closest points to the origin (0, 0). (Here, the d ...

  5. 最接近原点的K个点

    一.题目描述 我们有一个由平面上的点组成的列表 points.需要从中找出 K 个距离原点 (0, 0) 最近的点 这里,平面上两点之间的距离是欧几里德距离 你可以按任何顺序返回答案.除了点坐标的顺序 ...

  6. Leetcode973. K Closest Points to Origin最接近原点的K个点

    我们有一个由平面上的点组成的列表 points.需要从中找出 K 个距离原点 (0, 0) 最近的点. (这里,平面上两点之间的距离是欧几里德距离.) 你可以按任何顺序返回答案.除了点坐标的顺序之外, ...

  7. leetcode-973-最接近原点的K个点

    题目描述: 可参考:题215 方法一:排序 class Solution: def kClosest(self, points: List[List[int]], K: int) -> List ...

  8. LeetCode刷题总结-双指针、位运算和分治法篇

    本文总结LeetCode上有关双指针.位运算和分治法的算法题,推荐刷题总数14道.具体考点分析如下图: 一.双指针 1.字符串和数组问题 题号:424. 替换后的最长重复字符,难度中等 题号:828. ...

  9. LeetCode:堆专题

    堆专题 参考了力扣加加对与堆专题的讲解,刷了些 leetcode 题,在此做一些记录,不然没几天就忘光光了 力扣加加-堆专题(上) 力扣加加-堆专题(下) 总结 优先队列 // 1.java中有优先队 ...

随机推荐

  1. 微信小程序-展示后台传来的json格式数据

    昨天粗粗的写了下后台数据传到微信小程序显示,用来熟悉这个过程,适合刚入门学习案例: 需了解的技术:javaSE,C3p0,jdbcTemplate,fastjson,html,javaScript,c ...

  2. 0级搭建类008-Ubuntu Server Linux安装 (18.04.2) 公开

    项目文档引子系列是根据项目原型,制作的测试实验文档,目的是为了提升项目过程中的实际动手能力,打造精品文档AskScuti. 项目文档引子系列目前不对外发布,仅作为博客记录.如学员在实际工作过程中需提前 ...

  3. 使用ADO.NET 查询和操作数据

    一.使用StringBuilder类追加和删除字符串 1.创建StringBuilder类的对象 StringBuilder sb=new StringBuilder("初始字符串值&quo ...

  4. nodeJS菜鸟教程笔记

    http模块 var http = require('http'); // 引入http模块 var url = require('url'); // 引入url模块 var querystring ...

  5. C#依赖注入 简体demo

      class Program { static void Main(string[] args) { Dal dal = new MySql(); dal.Add(); Dal dal1 = new ...

  6. 爬虫爱用的一些python技巧

    1.正则表达式 有时候提取到的数据不规整,需要用正则来匹配所需要展现出来的数据 学习链接:https://www.cnblogs.com/-chenxs/p/11352172.html,https:/ ...

  7. 基于 Ant Desigin 的后台管理项目打包优化实践

    背景 按照 Ant Design 官网用 React 脚手构建的后台项目,刚接手项目的时候大概30条路由左右,我的用的机子是 Mac 8G 内存,打包完成需要耗时2分钟左右,决定优化一下. 项目技术栈 ...

  8. [AT3867] Digit Sum 2

    给出N,求小于等于N的正整数中用十进制表示各数位数字之和的最大值. Solution 如果是X999的形式,那么就是自己 否则,就是(X-1)999 #include <bits/stdc++. ...

  9. 使用VS2017创建EF框架实例

    本文例子中使用环境:vs2017,sql server 2008 一,创建EF项目 1,解决方案添加.Net Framework类库项目,在新建的项目下新建项:data->ADO.NET实体数据 ...

  10. 杭电oj1995——汉诺塔V(java实现)

    正文之前,先说下做这题的心路历程(简直心累) 这是今天下午的第一道题 第一次看到题目标题——汉诺塔 内心OS:wc,汉诺塔诶,听名字就很难诶,没做过诶,肯定很难实现吧,不行,我得去看看讲解 然后就上b ...