链接:https://ac.nowcoder.com/acm/contest/7031/E
来源:牛客网
题目描述
做完了检查之后,younik得知得要星期天才能拿到结果,于是她离开了校医院。她抬头看了看太阳,感觉自己实在是枵肠辘辘,饥不可堪。Younik早就听说陕西师范大学又叫陕西吃饭大学,她决定去陕师大食堂填饱肚子。
Younik走到食堂旁边,发现食堂门口居然也在排队(今天怎么到处都在排队),她上前一问,原来为了方便管理,食堂决定,每一个小时才允许大家进去一次,每次吃饭时间必须控制在半个小时以内,还有半个小时要消毒。
好不容易进入了食堂,younik随便找了个地方坐下。在等饭菜的时候,她发现一件事情:
1. 食堂是长方形的,而且是无限长的(有点奇怪,但是不要在意)。
2. 食堂的中间有一条无限长的平分线,把食堂分成了上下两半(就像是一个x坐标轴,把食堂分成了x为正和x为负)。平分线上可以放高温杀病毒的机器。
Younik非常好奇这些机器的工作原理,于是她请教了路过她的打饭从不手抖的肖阿姨。打饭从不手抖的肖阿姨说:
1. 每个人坐过的地方都需要消毒。
2. 机器可以清理半径为r的区域的所有病毒。
例如:如果有三个人(-2,2),(-2,-1),(2,0)。就需要至少两个机器才能覆盖这三个点,比如图上的两个机器分别放置在-2和1的地方。(机器人的坐标可以是非整数)
打饭从不手抖的肖阿姨想考考你,你能不能写一个程序,找到覆盖所有人坐过位置的最小数量的高温杀病毒的机器数量。每个人的座位会用x-y坐标表示。
输入描述:
输入由很多个案例组成,当案例以0 0开头时,表示没有案例了。
每个案例的组成如下:
第一行包含两个整数n (1<=n<=1000)和d(0<d<80),其中n是刚刚前来吃饭的人的数量,d是机器的消毒范围。接下来的n行,每行包含两个整数,代表每个人的坐标位置(坐标的值为整数,y轴的范围是正负200,x轴是正负1000)。
输出描述:
每个样例输出一行,表示需要的最小机器数量。
如果无解,则输出-1。
示例1
输入
复制3 1 -1 1 2 1 5 1 3 1 1 2 2 1 5 1 0 0
3 1 -1 1 2 1 5 1 3 1 1 2 2 1 5 1 0 0
输出
复制3 -1
3 -1
原题:poj1328
注意题目是看x轴上的。一样的题在洛谷是雷达安装。
一个座位的最左能到和最右能到的圆心边界点可以通过勾股定理求,然后如果前一个的右界端点>=后一个左界端点,覆盖这两个点的圆的半径<=d就可以满足(画个图可以发现区间∩其实连线长度<三角形最长边的d长度),所以d半径的圆一定满足。然后N^2暴力标记统计就好了。
#include<iostream>
#include<vector>
#include<queue>
#include<cstring>
#include<cmath>
#include<map>
#include<set>
#include<cstdio>
#include<algorithm>
#define debug(a) cout<<#a<<"="<<a<<endl;
using namespace std;
const int maxn=1e3+100;
typedef long long LL;
bool vis[maxn];
LL n,d;
struct P{
double x,y;
}a[maxn];
struct data{
double left,right;
}da[maxn];
bool cmp(data A,data B){
return A.right<B.right;
}
int main(void)
{
cin.tie(0);std::ios::sync_with_stdio(false);
while(cin>>n>>d&&n!=0&&d!=0){
memset(vis,0,sizeof(vis));
bool flag=1;
for(LL i=1;i<=n;i++) {
cin>>a[i].x>>a[i].y;
if(a[i].y>d||a[i].y<-d) flag=0;
}
for(LL i=1;i<=n;i++){
double mid=sqrt(1.0*d*d-1.0*a[i].y*a[i].y);
da[i].left=a[i].x-mid;
da[i].right=a[i].x+mid;
}
sort(da+1,da+1+n,cmp);
LL ans=0;
for(LL i=1;i<=n;i++){
if(!vis[i]){
vis[i]=true;
for(LL j=i+1;j<=n;j++){
if(!vis[j]&&da[i].right>=da[j].left){
vis[j]=true;
}
}
ans++;
}
}
if(flag)
cout<<ans<<endl;
else cout<<-1<<endl;
}
return 0;
}