【题目链接】
http://poj.org/problem?id=3179
【参考】
http://www.cnblogs.com/evenbao/p/9243183.html
【算法】
- 二分答案+判定
- 二维坐标的离散化去除不存在草的行和列
- 二维前缀和
- lower_bound (>=) upper_bound (>)
1 #include <stdio.h> 2 #include <algorithm> 3 #include <iostream> 4 using namespace std; 5 struct data{int x,y;}a[1010]; 6 int c,n,tot,i,j,tx,ty; 7 int rec[1010][1010],b[10010]; 8 void discrete() 9 { 10 sort(b+1, b+tot+1); 11 tot = unique(b+1, b+tot+1) - b - 1; 12 for(i = 1; i <= n; i++) { 13 tx = lower_bound(b+1,b+tot+1,a[i].x) - b; 14 ty = lower_bound(b+1,b+tot+1,a[i].y) - b; 15 rec[tx][ty]++; 16 } 17 b[++tot] = 10001; 18 for(i = 1; i <= tot; i++) 19 for(j = 1; j <= tot; j++) 20 rec[i][j] = rec[i-1][j] + rec[i][j-1] - rec[i-1][j-1] + rec[i][j]; 21 } 22 bool valid(int cur) 23 { 24 int p; 25 if(cur >= b[tot]) { return true; } 26 p = upper_bound(b+1, b+tot+1, b[tot]-cur+1) - b - 1; 27 for(i = 1; i <= p; i++) { 28 for(j = 1; j <= p; j++) { 29 tx = upper_bound(b+1, b+tot+1, b[i]+cur-1) - b - 1; 30 ty = upper_bound(b+1, b+tot+1, b[j]+cur-1) - b - 1; 31 if(rec[tx][ty] - rec[i-1][ty] - rec[tx][j-1] + rec[i-1][j-1] >= c) return true; 32 } 33 } 34 return false; 35 } 36 int main() 37 { 38 scanf("%d%d", &c, &n); 39 for(i = 1; i <= n; i++) 40 scanf("%d%d", &a[i].x, &a[i].y), 41 b[++tot] = a[i].x, b[++tot] = a[i].y; 42 discrete(); 43 int l = 1, r = 10000; 44 while(l<r) { 45 int mid = (l + r) >> 1; 46 if(valid(mid)) r = mid; 47 else l = mid + 1; 48 } 49 printf("%d ", l); 50 return 0; 51 }