题目链接:点击打开链接
Description
We use Cartesian coordinate system, defining the coasting is the x-axis. The sea side is above x-axis, and the land side below. Given the position of each island in the sea, and given the distance of the coverage of the radar installation, your task is to write a program to find the minimal number of radar installations to cover all the islands. Note that the position of an island is represented by its x-y coordinates.
Figure A Sample Input of Radar Installations
Input
The input is terminated by a line containing pair of zeros
Output
Sample Input
3 2
1 2
-3 1
2 1
1 2
0 2
0 0
Sample Output
Case 1: 2
Case 2: 1
题目大意:给出一些坐标,以x轴上的点为原点,d为半径画圆,问:如果想用这样的圆把所有的点全包围至少需要多少个圆,如果无法包围输出-1.
ps:一开始我是用的暴力搜索的办法,就是按x坐标排序,从小到大画圆.如果有重复的就更新.但是不能测试double型的.
所有一个将每个点的x坐标范围映射到x轴上得到一个区域.对每个区域排序,如果能共用一个圆即一个区域则少一个圆的++.
#include <iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<math.h>
#include<cstdlib>
using namespace std;
struct node
{
double l,r;
}q[1200];
bool cmp(node x,node y)
{
return x.l<y.l;
}
int main()
{
double d,x,y;//必须是double 型
int n;
int t=1;
while(scanf("%d%lf",&n,&d))//用cin会超时,
{
if(n==0&&d==0)break;
int f=1;
for(int i=0;i<n;i++)
{
cin>>x>>y;
q[i].l=x-sqrt(d*d-y*y);//映射点的区间范围
q[i].r=x+sqrt(d*d-y*y);
if(y>d||y<0||d<=0)f=0;
}
if(f==0)
{
printf("Case %d: -1\n",t);
t++;
continue;
}
sort(q,q+n,cmp);//对区间左点进行排序
double k;
k=q[0].r;
int sum=1;
for(int i=1;i<n;i++)
{
if(q[i].l>k)//两个点无重复区间,所以++
{
sum++;
k=q[i].r;
}
else if(q[i].r<k)//一个区间被另一个包含时,应对区间右点小的进行下一次的比较
{
k=q[i].r;
}
}
printf("Case %d: %d\n",t,sum);
t++;
}
return 0;
}