poj2002 哈希鏈地址法

Squares
Time Limit: 3500MS   Memory Limit: 65536K
Total Submissions: 19983   Accepted: 7691

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

4
1 0
0 1
1 1
0 0
9
0 0
1 0
2 0
0 2
1 2
2 2
0 1
1 1
2 1
4
-2 5
3 7
0 0
5 2
0

Sample Output

1
6
1

Source


給你座標上的一些點,問你最多能構成多少個正方形。
在座標上給出兩點計算能構成正方形的另外兩點的公式:

已知: (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)

這樣的做法會使一個正方形被枚舉四次,所以最後輸出要除以四。
用哈希標記每一個點,查詢時解決地址衝突的方法
#include<iostream>
#include<malloc.h>
#include<cstring>
using namespace std;
const int prime=1999;
struct Node
{
    int x,y;
};
struct HashTable
{
    int x,y;
    HashTable *next;
};
struct Node pos[1001];
struct HashTable *hashs[prime];

void insert_vist(int k)
{
    int key=(pos[k].x*pos[k].x+pos[k].y*pos[k].y)%prime+1;
    if(!hashs[key])
    {
        HashTable *temp=(struct HashTable*)malloc(sizeof(HashTable));

        temp->x=pos[k].x;
        temp->y=pos[k].y;
        temp->next=NULL;
        hashs[key]=temp;
    }
    else//hashs[key]地址已存,開放尋址
    {
        HashTable *temp=hashs[key];
        while(temp->next)  //直至temp->next爲NULL
            temp=temp->next;
        temp->next=(struct HashTable*)malloc(sizeof(HashTable));
        temp->next->x=pos[k].x;
        temp->next->y=pos[k].y;
        temp->next->next=NULL;
    }
    return;
}

bool finds(int x,int y)
{
    int key=(x*x+y*y)%prime+1;
    if(!hashs[key])
        return false;
    else
    {
        HashTable *temp=hashs[key];
        while(temp)
        {
            if(temp->x==x&&temp->y==y)
                return true;
            temp=temp->next;
        }
    }
    return false;
}

int main()
{
    int n;
    while(cin>>n)
    {
        if(n==0)
            break;
        memset(hashs,0,sizeof(hashs));
        for(int k=1;k<=n;k++)
        {
            cin>>pos[k].x>>pos[k].y;
            insert_vist(k);
        }
        int num=0;
        for(int i=1;i<=n-1;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(finds(x3,y3)&&finds(x4,y4))
                    num++;
                x3=pos[i].x-b;
                y3=pos[i].y+a;
                x4=pos[j].x-b;
                y4=pos[j].y+a;
                if(finds(x3,y3)&&finds(x4,y4))
                    num++;

            }
        }
        cout<<num/4<<endl;
    }
    return 0;
}

用鏈地址法。
代碼:
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章