2014-05-08 05:16

题目链接

原题:

Given a circle with N defined points and a point M outside the circle, find the point that is closest to M among the set of N. O(LogN)

题目:给定一个圆上的N个点,和一个在这个圆外部的点。请找出这N个点中与外部点最近的那个。要求时间复杂度是对数级的。

解法1:这位“Guy”老兄又出了一道莫名奇妙的题:1. 这些点是等距离的吗?2. 这些点是顺时针还是逆时针排列的?在没有比较清楚思路的情况下,我只写了个O(n)枚举的算法。

代码:

 // http://www.careercup.com/question?id=4877486110277632
#include <cmath>
#include <iostream>
#include <vector>
using namespace std; struct Point {
double x;
double y;
Point(double _x = , double _y = ): x(_x), y(_y) {};
}; double dist(const Point &p1, const Point &p2)
{
return sqrt((p1.x - p2.x) * (p1.x - p2.x) + (p1.y - p2.y) * (p1.y - p2.y));
} int main()
{
int i, n;
Point pout;
vector<Point> vp;
int min_i;
double d, min_d; while (cin >> n && n > ) {
vp.resize(n);
for (i = ; i < n; ++i) {
cin >> vp[i].x >> vp[i].y;
}
cin >> pout.x >> pout.y; min_i = ;
min_d = dist(pout, vp[]);
for (i = ; i < n; ++i) {
d = dist(pout, vp[i]);
min_i = d < min_d ? i : min_i;
}
cout << '(' << vp[min_i].x << ',' << vp[min_i].y << ')' << endl;
cout << min_d << endl;
vp.clear();
} return ;
}

解法2:实际上这题不但有对数级算法,还有常数级算法。但有一个额外条件需要满足:我得知道圆心在哪儿。计算圆心需要把所有点的坐标求平均值,那样的算法复杂度还是线性的。如果我们定义P[i]为圆上的那N个点,O为圆心,M为圆外的那个点。那么我们连接OP[i]与OM,可以发现OM与OP[i]的夹角分布是循环有序的(参见Leetcode里面的Rotated Sorted Array),条件是这N个点呈顺时针或逆时针分布。你可以通过二分得到距离最小的结果,但更快的算法是常数级的。你只要计算一个夹角,就知道所有的了。因为这些夹角是个等差数列。比如四个点中,有一个的夹角是73°,那么另外三个肯定是163°、107°(253°)、17°(343°)。谁的距离最短呢?角度最小的就是了,注意优角要换算成锐角或钝角。想要通过一次计算就解决问题,用除法和取模的思想吧。此处的代码默认点是按照顺时针排列的,否则为了判断哪个方向,又得进行一些计算。那样的话,代码都乱的看不清楚了。

代码:

 // http://www.careercup.com/question?id=4877486110277632
#include <cmath>
#include <iostream>
#include <vector>
using namespace std; struct Point {
double x;
double y;
Point(double _x = , double _y = ): x(_x), y(_y) {}; Point operator - (const Point &other) {
return Point(x - other.x, y - other.y);
}; Point operator + (const Point &other) {
return Point(x + other.x, y + other.y);
}; double operator * (const Point &other) {
return x * other.x + y * other.y;
};
}; double dist(const Point &p1, const Point &p2)
{
return sqrt((p1.x - p2.x) * (p1.x - p2.x) + (p1.y - p2.y) * (p1.y - p2.y));
} int main()
{
int i, n;
Point pout;
vector<Point> vp;
Point center;
Point v0, vout;
// the angle between OM and a line of center
double angle;
// 2 * pi / n
double side_angle;
const double pi = 3.1415926;
double d; while (cin >> n && n > ) {
vp.resize(n);
for (i = ; i < n; ++i) {
cin >> vp[i].x >> vp[i].y; }
cin >> center.x >> center.y;
cin >> pout.x >> pout.y; v0 = vp[] - center;
vout = pout - center; side_angle = * pi / n;
angle = arccos((v0 * vout) / (dist(vp[], center) * dist(pout, center)));
d = angle / side_angle;
// Here I assume the points are arranged in clockwise order.
i = d - floor(d) < 0.5 ? floor(d) : floor(d) + ;
cout << vp[i].x << ' ' << vp[i].y << endl; vp.clear();
} return ;
}

Careercup - Google面试题 - 4877486110277632的更多相关文章

  1. Careercup - Google面试题 - 5732809947742208

    2014-05-03 22:10 题目链接 原题: Given a dictionary, and a list of letters ( or consider as a string), find ...

  2. Careercup - Google面试题 - 5085331422445568

    2014-05-08 23:45 题目链接 原题: How would you use Dijkstra's algorithm to solve travel salesman problem, w ...

  3. Careercup - Google面试题 - 4847954317803520

    2014-05-08 21:33 题目链接 原题: largest number that an int variable can fit given a memory of certain size ...

  4. Careercup - Google面试题 - 6332750214725632

    2014-05-06 10:18 题目链接 原题: Given a ,) (,) (,), (,) should be returned. Some suggest to use Interval T ...

  5. Careercup - Google面试题 - 5634470967246848

    2014-05-06 07:11 题目链接 原题: Find a shortest path ,) to (N,N), assume is destination, use memorization ...

  6. Careercup - Google面试题 - 5680330589601792

    2014-05-08 23:18 题目链接 原题: If you have data coming in rapid succession what is the best way of dealin ...

  7. Careercup - Google面试题 - 5424071030341632

    2014-05-08 22:55 题目链接 原题: Given a list of strings. Produce a list of the longest common suffixes. If ...

  8. Careercup - Google面试题 - 5377673471721472

    2014-05-08 22:42 题目链接 原题: How would you split a search query across multiple machines? 题目:如何把一个搜索que ...

  9. Careercup - Google面试题 - 6331648220069888

    2014-05-08 22:27 题目链接 原题: What's the tracking algorithm of nearest location to some friends that are ...

随机推荐

  1. .NET Web开发总结(五)

    7 常用服务器控件 7.1 服务器控件概述 · 服务器控件是指在服务器上执行程序的代码的组件 通常这些服务器控件会提供    给用户一定的界面,  以便用户与服务器之间快速的交互 7.2 HTML 服 ...

  2. 破解source insignt方法

    source insignt版本:官网3.5版本 方法:在桌面建立一个文本文档,将下面内容拷贝进去,保存为.reg文件(注意拓展名问题,自己设置),然后双击即可. win7  64bit Window ...

  3. c#操作xml增删改查

    1.首先新建一个xml文件(Root是我写上的) 2. 3.直接上代码,更直观 (1)初始化xml /// <summary> /// 初始化xml /// </summary> ...

  4. jQuery插件Skippr实现焦点图

    史上效果最好的焦点图幻灯片jQuery插件Skippr,轻量级插件.响应式布局插件,强大的参数自定义 配置,可自定义切换速度.切换方式.是否显示左右箭头.是否自动播放.自动播放间隔时间等配置 参数,调 ...

  5. VS2008调试快捷键

    F5: 启动调试 Ctrl+F5: 开始执行(不调试) F10: 逐过程(不进入函数单步) F11: 逐语句(进入函数单步) Shift+F11跳出(实用) Ctrl+F10: 运行到光标处 F6: ...

  6. Silverlight 独立存储(IsolatedStorageFile)

    1.在Web中添加天气服务引用地址 http://www.webxml.com.cn/WebServices/WeatherWebService.asmx?wsdl 2.在Web中添加Wcf服务接口I ...

  7. 四、MongoDB的查询

    一.MongoDB的下载.安装与部署 二.MongoDB的基础知识简介 三.MongoDB的创建.更新和删除 db.blogs.insert([ { "author": " ...

  8. Spring中Quartz调度器的使用

    一.Quartz的特点 * 按作业类的继承方式来分,主要有以下两种: 1.作业类继承org.springframework.scheduling.quartz.QuartzJobBean类的方式 2. ...

  9. centos6.3安装nginx

    一般使用linux系统的不少网友可能都是直接使用一键安装包进行安装的,以前作者也这样,但是很多时候这些一键安装方便是方便但是可能在升级及其他很多地方不是很好,本文就说下在centos6.3安装ngin ...

  10. Delphi中nil和null的区别

    nil:空指针,空地址,对象也是指针,可以object := nil;null:是一个未定义值的变量,既不是0也不代表空字符串,它是未定义的.