• POJ 2002 统计正方形 HASH


    题目链接:http://poj.org/problem?id=2002

    题意:给定n个点,问有多少种方法可以组成正方形。

    思路:我们可以根据两个点求出对应正方形[有2个一个在两点左边,一个在两点右边]另外两个点的左边。例如

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

    枚举两个点,进行HASH,然后再枚举两个点然后求另外两个点,再从HASH表找,冲突用拉链法。

    这种做法会使同一个正方形按照不同的顺序被枚举了四次,因此最后的结果要除以4.

    #include<iostream>
    #include<algorithm>
    #include<cstring>
    #include<cstdio>
    #include<string>
    #include<vector>
    #include<cmath>
    #include<set>
    using namespace std;
    typedef long long int LL;
    typedef unsigned int uint;
    const int MAXN=1000+5;
    const int MOD=99991;
    struct Point{
        int x,y;
        Point(int a=0,int b=0):x(a),y(b){};
    };
    Point P[MAXN];
    vector<Point>Hash[MOD];
    void Init(){
        for(int i=0;i<MOD;i++){
            Hash[i].clear();
        }
    }
    void InsetHash(Point a){
        int Num=(a.x*a.x+a.y*a.y)%MOD;
        Hash[Num].push_back(a);
    }
    bool Search(Point a){
        int Num=(a.x*a.x+a.y*a.y)%MOD;
        for(int i=0;i<Hash[Num].size();i++){
            if(a.x==Hash[Num][i].x&&a.y==Hash[Num][i].y){
                return true;
            }
        }
        return false;
    }
    int main(){
    #ifdef kirito
        freopen("in.txt","r",stdin);
        freopen("out.txt","w",stdout);
    #endif
        int n;
        while(scanf("%d",&n)&&n){
            int ans=0; Init();
            for(int i=0;i<n;i++){
                scanf("%d %d",&P[i].x,&P[i].y);
            }
            for(int i=0;i<n;i++){
                InsetHash(P[i]);
            }
            for(int i=0;i<n;i++){
                for(int j=i+1;j<n;j++){
                    Point C,D;
                    C.x=P[i].x+(P[i].y-P[j].y); C.y=P[i].y-(P[i].x-P[j].x);
                    D.x=P[j].x+(P[i].y-P[j].y); D.y=P[j].y-(P[i].x-P[j].x);
                    if(Search(C)&&Search(D)){
                        ans++;
                    }
                    C.x=P[i].x-(P[i].y-P[j].y); C.y=P[i].y+(P[i].x-P[j].x);
                    D.x=P[j].x-(P[i].y-P[j].y); D.y=P[j].y+(P[i].x-P[j].x);
                    if(Search(C)&&Search(D)){
                        ans++;
                    }
                }
            }
            printf("%d
    ",ans>>2);
        }
        return 0;
    }
  • 相关阅读:
    关于《Spark快速大数据分析》运行例子遇到的报错及解决
    把打印的内容保存成文件(PDF)
    浏览器升级提示网站:《快乐浏览》
    apache server-status配置
    Centos7安装完毕后联网-设置ip地址(VMware虚拟机)
    centos中apache自用常用额外配置记录(xwamp)
    ie浏览器升级的正确姿势
    有道云笔记web版本居然不支持火狐
    php 单文件测试代码时必加入的代码
    php简易配置函数
  • 原文地址:https://www.cnblogs.com/kirito520/p/5645712.html
Copyright © 2020-2023  润新知