Assume the coasting is an infinite straight line. Land is in one side of coasting, sea in the other. Each small island is a point locating in the sea side. And any radar installation, locating on the coasting, can only cover d distance, so an island in the sea can be covered by a radius installation, if the distance between them is at most d.
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
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
The input consists of several test cases. The first line of each case contains two integers n (1<=n<=1000) and d, where n is the number of islands in the sea and d is the distance of coverage of the radar installation. This is followed by n lines each containing two integers representing the coordinate of the position of each island. Then a blank line follows to separate the cases.
The input is terminated by a line containing pair of zeros
The input is terminated by a line containing pair of zeros
For each test case output one line consisting of the test case number followed by the minimal number of radar installations needed. "-1" installation means no solution for that case.
3 2 1 2 -3 1 2 1 1 2 0 2 0 0
Case 1: 2 Case 2: 1
/* 题解:贪心策略 以小岛为圆心画圆,与X轴相交两点 再按照左端点从小到大排序 最后贪心过一遍就OK了 */ #include <iostream> #include<math.h> #include<algorithm> #include<stdio.h> using namespace std; struct pos { int x, y; }nowpos[1005]; int flag = 1; struct node { double left, right; }nownode[1005]; int d, n; bool cmp(node ss, node tt) { return ss.left < tt.left; } void Cal() { for (int i = 0; i < n; i++) { nownode[i].left = nowpos[i].x - ((double)sqrt(pow(d,2) - pow(nowpos[i].y,2))); nownode[i].right = nowpos[i].x + ((double)sqrt(pow(d, 2) - pow(nowpos[i].y, 2))); } } int FinaAns() { int cnt = 1; sort(nownode, nownode + n, cmp);//按照左端点从小到大排序 double temp = nownode[0].right; //贪心算法 for (int i = 1; i < n; i++) { //没注意到就Wrong了,重点^_^||| //后面的右端点可以直接小于之前的右端点 //这样就要更新右端点 if (nownode[i].right < temp) { temp = nownode[i].right; } else if (temp < nownode[i].left) { cnt++; temp = nownode[i].right; } } return cnt; } int main() { int tempcount = 0; while (cin >> n >> d) { flag = 1; if (n == 0 && d == 0) break; for (int i = 0; i < n; i++) { scanf("%d%d", &nowpos[i].x, &nowpos[i].y); if (nowpos[i].y > d) { flag = 0; } } if (flag == 0) { //找了半天的错原来就是这里少了个Case,Q_Q printf("Case %d: -1\n", ++tempcount); } else { Cal();//计算 printf("Case %d: %d\n", ++tempcount, FinaAns());//输出答案 } } return 0; }