poj 2002 Squares

来源:互联网 发布:免费喊单软件 编辑:程序博客网 时间:2024/05/23 14:41

Squares
Time Limit: 3500MS Memory Limit: 65536KTotal Submissions: 15879 Accepted: 6009

Description

A square is a 4-sided polygon whose sides have equal length and adjacent sides form 90-degree angles. It is also a polygon such that rotating about its centre by 90 degrees gives the same polygon. It is not the only polygon with the latter property, however, as a regular octagon also has this property. 

So we all know what a square looks like, but can we find all possible squares that can be formed from a set of stars in a night sky? To make the problem easier, we will assume that the night sky is a 2-dimensional plane, and each star is specified by its x and y coordinates. 

Input

The input consists of a number of test cases. Each test case starts with the integer n (1 <= n <= 1000) indicating the number of points to follow. Each of the next n lines specify the x and y coordinates (two integers) of each point. You may assume that the points are distinct and the magnitudes of the coordinates are less than 20000. The input is terminated when n = 0.

Output

For each test case, print on a line the number of squares one can form from the given stars.

Sample Input

41 00 11 10 090 01 02 00 21 22 20 11 12 14-2 53 70 05 20

Sample Output

161

题目大意:

给你在纸面的n个点的x坐标以及y坐标,在这些点中能找到几个正方形。

这几天在做hash,见到这个题目还是没有太多的思路,后来看别人博客发现是hash每个点到(0,0)的距离而进行统计的。

也就是说把每个点的坐标都先统计进一个结构(先后用的链表以及vector的写法)中,按照到原点的距离来分类。

然后统计的时候是在1~n以及i+1~n中统计每两个点符合条件的另外两个点,几何推一下很容易可以得出来


如何避免冲突,下面有两种写法:

方法一:(链表)

也算复习一下学过的数据结构

个人感觉太过冗长.......  代码水平太差....... 感觉一不小心就会写搓

#include<iostream>#include<stdio.h>#include<cstring >using namespace std;#define mod 1999   //最好定义成小于2*n的最大素数struct node{    int x;    int y;};struct  HashTable{    int x;    int y;    HashTable *next;    HashTable()    {        next=0;    }};node pos[1001];HashTable *hash[mod];void insert(int k){    int key=(pos[k].x*pos[k].x+pos[k].y*pos[k].y)%mod;    if(!hash[key])    {        HashTable* temp=new HashTable;        temp->x=pos[k].x;        temp->y=pos[k].y;        hash[key]=temp;    }    else    {        HashTable* temp=hash[key];  //这一步之前错了,之前申请的不是一个链表,是一个hashtable结点,值存了一个元素        while(temp->next)            temp=temp->next;        temp->next=new HashTable;        temp->next->x=pos[k].x;        temp->next->y=pos[k].y;    }    return;}bool find(int a,int b){    int key=(a*a+b*b)%mod;    if(!hash[key]) return false;    else    {        HashTable *temp=hash[key];        while(temp)        {            if(temp->x==a && temp->y==b) return true;            temp=temp->next;        }    }    return false;}int main (){    int n;    while(cin>>n)    {        if(n==0) break;        memset(hash,0,sizeof(hash));        for(int i=1; i<=n; i++)        {            scanf("%d%d",&pos[i].x,&pos[i].y);            insert(i);        }        int num=0;        for(int i=1;i<=n;i++)         for(int j=i+1;j<=n;j++)         {             int a=pos[j].x-pos[i].x;             int b=pos[j].y-pos[i].y;             int x3=pos[i].x-b;             int y3=pos[i].y+a;             int x4=pos[j].x-b;             int y4=pos[j].y+a;             if(find(x3,y3) && find(x4,y4))             printf("* %d %d * %d %d*\n",x3,y3,x4,y4),             num++;             x3=pos[i].x+b;             y3=pos[i].y-a;             x4=pos[j].x+b;             y4=pos[j].y-a;             if(find(x3,y3) && find(x4,y4))             printf("* %d %d * %d %d*\n",x3,y3,x4,y4),             num++;         }//         for(int i=0;i<=100;i++)//         {//              if(hash[i])//              {//                   HashTable *temp=hash[i];//                   cout<<i<<" **";//                   while(temp)//                   {//                         cout<<temp->x<<" "<<temp->y<<"**";//                         temp=temp->next;//                   }//                   cout<<endl;//              }////         }         cout<<num/4<<endl;  //同一个正方形枚举了4次    }}/*160 10 20 30 41 11 21 31 42 12 22 32 43 13 23 33 4*/


方法二:vector写法

简单多了,明了多了,好用........

#include<iostream>#include<stdio.h>#include<vector>using namespace std;#define mod 1999struct point{    int x,y;};point p[1005];vector<int> hash[2000];bool find(int a,int b){    int key=(a*a+b*b)%mod;    for(vector<int>::size_type j = 0; j < hash[key].size(); j++ )    {        if(p[ hash[key][j] ].x==a && p[ hash[key][j] ].y==b) return true;    }    return false;}void insert(int k){    int key=( p[k].x*p[k].x + p[k].y*p[k].y )%mod;    hash[key].push_back(k);}int main (){    int n;    while(~scanf("%d",&n))    {        if(n==0) break;        int num=0;        for(int i=0;i<1999;i++)        hash[i].clear();        for(int i=1;i<=n;i++)        {            scanf("%d%d",&p[i].x,&p[i].y);            insert(i);        }       for(int i=1;i<=n;i++)         for(int j=i+1;j<=n;j++)         {             int a=p[j].x-p[i].x;             int b=p[j].y-p[i].y;             int x3=p[i].x-b;             int y3=p[i].y+a;             int x4=p[j].x-b;             int y4=p[j].y+a;             if(find(x3,y3) && find(x4,y4))             //printf("* %d %d * %d %d *\n",x3,y3,x4,y4),             num++;             x3=p[i].x+b;             y3=p[i].y-a;             x4=p[j].x+b;             y4=p[j].y-a;             if(find(x3,y3) && find(x4,y4))             //printf("* %d %d * %d %d *\n",x3,y3,x4,y4),             num++;         }         cout<<num/4<<endl;    }}
wa了好几发是因为......每个case里面没有清空vector........多case要注意清空和初始化


0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 自考毕业证出生日期错误怎么办 成考没有学位证怎么办 评职称学历认证怎么办 国家不承认学历怎么办 高考分数错了怎么办 签合同了不想干怎么办 贵港教育小学插班生怎么办 学校宿舍限瓦怎么办 苹果锁屏后wifi断开怎么办 兼职一天不给钱怎么办 五月孩子掉床怎么办 孩子五月份掉床怎么办 郑州怎么办暂住证凭条 郑州居住证凭条怎么办 宿舍虫子咬人怎么办 is语音注册频繁怎么办 苹果id注销了怎么办 网站突然打不开了怎么办 谷歌邮箱打不开怎么办 360借款无力承担怎么办 公司被收购期权怎么办 创业板连续亏损怎么办 国企合并后员工怎么办 资金密码忘记了怎么办? 大华电子秤称重不准怎么办 股票暂停上市散户怎么办 入股公司赔钱了怎么办 家里被虚报脱贫怎么办 技术入股想退股怎么办 想开店没有资金怎么办 想开店资金不够怎么办 要开店没资金怎么办 想开店缺少资金怎么办 刚刚开店没有资金怎么办 有专利没钱投资怎么办 肉牛养殖没资金怎么办 入股分红想撤资怎么办 入股后想退股怎么办 土地使用权到期后怎么办 员工辞职扣工资怎么办 公司老板要跑路不发工资怎么办