标签:style blog http color os ar 使用 for sp
题意:给定n<=100000个二维点,并且0<=x,y<=100000,求有多少个平行于坐标轴的正方形
思路:本来想hash的,但是感觉不好弄。。
后来感觉像是分块,最坏的情况就是那种x,y点稠密在一起的情况,并且x与y大致相同的情况下答案最多。。
然后就想到了跟分块很像的暴力。
对于每个点,用vx[x]记录有p.x==x的点的y,用vy[y]记录p.y==y的x
那么对于每个vx[], vy[]排序。。
接着对于每个点我们统计以它为右上角的正方形。。
那么对于每个点(x, y),我们二分查找x处于vy[y]的位置ty,我们二分查找y处于vx[x]的位置tx
那么如果tx<ty,我们直接统计vx[x][0]~vx[x][tx-1]的所有y是否有符合的
每次判断可以通过使用二分查找其他点是否存在。。
如果tx>=ty则统计vy[y][0]~vy[y][ty-1]的所有y是否符合。方法类似。
这样最坏情况下应该跟分块的复杂度差不多吧(不会证明)
code:
1 #include <bits/stdc++.h> 2 #define M0(x) memset(x, 0, sizeof(x)) 3 #define MP make_pair 4 #define PB push_back 5 #define repf(i, a, b) for (int i = (a); i <= (b); ++i) 6 using namespace std; 7 #define x first 8 #define y second 9 const int maxn = 101010; 10 pair<int, int> p[maxn]; 11 vector<int> vx[maxn], vy[maxn]; 12 int n, m; 13 14 void solve(){ 15 int mx = 0, my = 0; 16 repf(i, 1, n){ 17 scanf("%d%d", &p[i].x, &p[i].y); 18 mx = max(p[i].x, mx); 19 my = max(p[i].y, my); 20 } 21 repf(i, 0, mx) vx[i].clear(); 22 repf(i, 0, my) vy[i].clear(); 23 repf(i, 1, n){ 24 vx[p[i].x].PB(p[i].y); 25 vy[p[i].y].PB(p[i].x); 26 } 27 repf(i, 0, mx) sort(vx[i].begin(), vx[i].end()); 28 repf(i, 0, my) sort(vy[i].begin(), vy[i].end()); 29 int ans = 0; 30 int tx, ty, x, y, t2, t3, d, nx, ny; 31 repf(i, 1, n){ 32 x = p[i].x, y = p[i].y; 33 tx = lower_bound(vx[x].begin(), vx[x].end(), y) - vx[x].begin(); 34 ty = lower_bound(vy[y].begin(), vy[y].end(), x) - vy[y].begin(); 35 if (tx < ty){ 36 t2 = ty; 37 for (int j = tx-1; j >= 0; --j){ 38 d = y - vx[x][j]; 39 nx = x - d; 40 t2 = lower_bound(vy[y].begin(), vy[y].end(), nx) - vy[y].begin(); 41 if (vy[y][t2] == nx){ 42 t3 = lower_bound(vx[nx].begin(), vx[nx].end(), vx[x][j]) - vx[nx].begin(); 43 if (vx[nx][t3] == vx[x][j]) ++ans; 44 } 45 } 46 continue; 47 } 48 // t2 = tx; 49 for (int j = ty-1; j >= 0; --j){ 50 d = x - vy[y][j]; 51 ny = y - d; 52 t2 = lower_bound(vx[x].begin(), vx[x].end(), ny) - vx[x].begin(); 53 if (vx[x][t2] == ny){ 54 t3 = lower_bound(vy[ny].begin(), vy[ny].end(), vy[y][j]) - vy[ny].begin(); 55 if (vy[ny][t3] == vy[y][j]) ++ans; 56 } 57 } 58 } 59 cout << ans << endl; 60 } 61 62 int main(){ 63 // freopen("a.in", "r", stdin); 64 // freopen("a.out", "w", stdout); 65 while (scanf("%d", &n) != EOF){ 66 solve(); 67 } 68 return 0; 69 }
标签:style blog http color os ar 使用 for sp
原文地址:http://www.cnblogs.com/yzcstc/p/4066266.html