POJ2002-二维哈希&数学定理&判断矩形-Squares

xiaoxiao2021-02-28  172

http://poj.org/problem?id=2002 给定一些点,问你这些点能组成多少矩形qwq 多校的时候遇到过一道,当时队友推了好久这个公式。 就是 当矩形确定两个点后。 剩余的点分别为 已知: (x1,y1) (x2,y2) 则: x3=x1+(y1-y2) y3= y1-(x1-x2) x4=x2+(y1-y2) y4= y2-(x1-x2) 或 x3=x1-(y1-y2) y3= y1+(x1-x2) x4=x2-(y1-y2) y4= y2+(x1-x2) 于是代码就好办多了。由于很多点,开不了那么大的数组qwq,所以用平方取余法来哈希,链表法来避免冲突qwq

#include <iostream> #include <cstdio> #include <cstdlib> #include <list> /* 自己写一个链表来模拟一下 用链式前进星 更好。 */ using namespace std; const int maxn=1006; const int mod=10017; list<pair<int,int> > hash1[mod+1]; void Push(int x,int y){ int tmp=(x*x+y*y)%mod; hash1[tmp].push_back(make_pair(x,y)); } bool seek(int x,int y){ int ans=(x*x+y*y)%mod; list<pair<int,int> >::iterator i;//没有这俩:: 会出来莫名的错误qwq if(!hash1[ans].size()) return false; for(i=hash1[ans].begin();i!=hash1[ans].end();i++){ if(i->first==x&&i->second==y) return true; } return false; } int main() { int t; int a[maxn],b[maxn]; while(~scanf("%d",&t)){ for(int i=0;i<mod+1;i++) hash1[i].clear(); if(!t) break; for(int i=0;i<t;i++){ scanf("%d%d",&a[i],&b[i]); Push(a[i],b[i]); } long long sum=0; for(int i=0;i<t;i++){ for(int j=i+1;j<t;j++){ if(i==j) continue; int x3=a[i]+(b[i]-b[j]); int y3=b[i]-(a[i]-a[j]); int x4=a[j]+(b[i]-b[j]); int y4=b[j]-(a[i]-a[j]); if(seek(x3,y3)&&seek(x4,y4)) sum++; } } for(int i=0;i<t;i++){ for(int j=i+1;j<t;j++){ if(i==j) continue; int x3=a[i]-(b[i]-b[j]); int y3=b[i]+(a[i]-a[j]); int x4=a[j]-(b[i]-b[j]); int y4=b[j]+(a[i]-a[j]); if(seek(x3,y3)&&seek(x4,y4)) sum++; } } printf("%lld\n",sum/4); } return 0; }
转载请注明原文地址: https://www.6miu.com/read-18333.html

最新回复(0)