AtCoder Beginner Contest 075 D - Axis-Parallel Rectangle
https://beta.atcoder.jp/contests/abc075/tasks/abc075_d
题意:
给出坐标平面上n个点的坐标,要求找到一个面积最小的矩形使得这个矩形的边界加上内部的点的数量大于等于k。
思路:
由于坐标过大,所以离散化。
离散化之后用前缀和,但是Orz求前缀和的时候写错了。
枚举左下角和右上角的坐标,分别为(i,j)和(s,e)。
那么点的数量为sum[s][e] - sum[s][j-1] - sum[i-1][q] + sum[i-1][j-1],切记,切记,画图画图。
代码:
1 #include <stdio.h> 2 #include <string.h> 3 #include <algorithm> 4 #include <map> 5 using namespace std; 6 7 struct node 8 { 9 int x,y; 10 } a[55]; 11 12 map<int,int> mpx,mpy; 13 map<int,int> invx,invy; 14 15 int sum[55][55]; 16 int b[55][55]; 17 18 bool cmp1(node aa,node bb) 19 { 20 return aa.x < bb.x; 21 } 22 23 bool cmp2(node aa,node bb) 24 { 25 return aa.y < bb.y; 26 } 27 28 int main() 29 { 30 int n,k; 31 32 scanf("%d%d",&n,&k); 33 34 for (int i = 1;i <= n;i++) 35 { 36 scanf("%d%d",&a[i].x,&a[i].y); 37 } 38 39 long long ans; 40 41 sort(a+1,a+n+1,cmp1); 42 43 for (int i = 1;i <= n;i++) 44 { 45 invx[i] = a[i].x; 46 mpx[a[i].x] = i; 47 } 48 49 long long dx = a[n].x - a[1].x; 50 51 sort(a+1,a+n+1,cmp2); 52 53 for (int i = 1;i <= n;i++) 54 { 55 invy[i] = a[i].y; 56 mpy[a[i].y] = i; 57 } 58 59 long long dy = a[n].y - a[1].y; 60 61 ans = dx * dy; 62 63 for (int i = 1;i <= n;i++) 64 { 65 int x = a[i].x,y = a[i].y; 66 67 b[mpx[x]][mpy[y]] = 1; 68 } 69 70 for (int i = 1;i <= n;i++) 71 for (int j = 1;j <= n;j++) 72 { 73 sum[i][j] = sum[i-1][j] + sum[i][j-1] - sum[i-1][j-1] + b[i][j]; 74 } 75 76 for (int i = 1;i <= n;i++) 77 for (int j = 1;j <= n;j++) 78 { 79 for (int s = i;s <= n;s++) 80 for (int q = j;q <= n;q++) 81 { 82 if (sum[s][q] - sum[s][j-1] - sum[i-1][q] + sum[i-1][j-1] >= k) 83 { 84 long long dx = invx[s] - invx[i]; 85 long long dy = invy[q] - invy[j]; 86 87 long long tmp = abs(dx) * abs(dy); 88 89 ans = min(ans,tmp); 90 } 91 } 92 } 93 94 printf("%lld\n",ans); 95 96 return 0; 97 }
康复训练中~欢迎交流!