最近点对问题 Swust Oj 794
2016-04-12 22:52
344 查看
Swust oj 794
问题描述:
设p1=(x1,
y1),
p2=(x2,
y2),
…, pn=(xn,
yn)是平面上n个点构成的集合S,设计算法找出集合S中距离最近的点对。
多组测试数据,第一行为测试数据组数n(0<n≤100),每组测试数据由两个部分构成,第一部分为一个点的个数m(0<m≤1000),紧接着是m行,每行为一个点的坐标x和y,用空格隔开,(0<x,y≤100000)
每组测试数据输出一行,为该组数据最近点的距离,保留4为小数。
问题描述:
设p1=(x1,
y1),
p2=(x2,
y2),
…, pn=(xn,
yn)是平面上n个点构成的集合S,设计算法找出集合S中距离最近的点对。
多组测试数据,第一行为测试数据组数n(0<n≤100),每组测试数据由两个部分构成,第一部分为一个点的个数m(0<m≤1000),紧接着是m行,每行为一个点的坐标x和y,用空格隔开,(0<x,y≤100000)
每组测试数据输出一行,为该组数据最近点的距离,保留4为小数。
#include<stdio.h> #include<cmath> #include<algorithm> #define MAX 1001 #define INF 1000000001 struct Point { double x, y; }point[MAX]; int n, temp[MAX]; bool cmp(Point a, Point b) // 点按照从左到右从下到上的方式排序 { if (a.x != b.x) { return a.x < b.x; } else { return a.y < b.y; } } bool cmpy(int a,int b) /按照y值大小排序 { return point[a].y < point[b].y; } double Min(double a, double b) //两个数的最小值,用来更新结果。 { return a < b ? a : b; } double Distance(int i, int j) //计算两个点的距离 { return sqrt((point[i].x - point[j].x) * (point[i].x - point[j].x) + (point[i].y - point[j].y) * (point[i].y - point[j].y)); } double Marge(int left, int right) //这里的参数为点集合的左右 { double d = INF; if (left == right) //如果左边的点等于右边的点,结束,返回d值 return d; if (left + 1 == right) //如果是挨着的两个点,计算距离()划分到最小时 { return Distance(left, right); } int mid = (left + right) / 2; //分治 double dis_left = Marge(left, mid); double dis_right = Marge(mid+1, right); d = Min(dis_left, dis_right); //让d 为分治后的最小距离 int i, j; int k = 0; for (i = left; i <= right; i++) //处理夸区域问题 { if (fabs(point[i].x - point[mid].x) <= d) //如果跨区域的点之间的距离小于等于d,那么我们就要加入数组做处理 { temp[k++] = i; } } sort(temp, temp + k, cmpy); 按照y值的从小到大排序 for (i = 0; i < k; i++) { for (j = i + 1; j < k &&point[temp[j]].y - point[temp[i]].y < d; j++) //求出跨区域的最短距离 { double temp_dis = Distance(temp[i], temp[j]); if (d>temp_dis) ///得出结果 { d = temp_dis; } } } return d; } int main() { int n, T; scanf("%d",&n); int i; while (n > 0) { scanf("%d",&T); for (i = 0; i < T; i++) { cin >> point[i].x >> point[i].y; } sort(point, point + T, cmp); printf( "%.4lf\n",Marge(0, T-1)); n--; } return 0; }
相关文章推荐
- 关于求解最大子序列和问题的总结
- ASP.NET Core中的依赖注入(5): ServiceProvider实现揭秘 【解读ServiceCallSite 】
- 第六周 可执行代码 以及 PSP 燃尽图 等等
- 加入逻辑线程
- C语言中的Bool类型
- python 实现 netcat
- 手把手教你将本地项目文件上传至github
- Java枚举类
- MD5 学习
- c++面试题链接
- 擅长排列的小明和D的小L
- nyoj 44 子串和<水哦>
- ThinkPHP3.2.3-文章管理系统-附带源码地址
- CQOI2016流水账
- Hibernate映射集合(JDK以及嵌入式值类)
- codeforces 569C C. Primes or Palindromes?(素数筛+dp)
- Java获取 JVM 运行信息
- 信管师培训之第十一节课作业(法律法规+标准规范+职业道德)
- 关于Qt使用MySQL的体会
- View绘制流程(3)---scroller 和 scrollTo srollBy