FZU 2231平行四边形【几何】

题目主干:

Problem 2231 平行四边形数

Accept: 225    Submit: 753
Time Limit: 2000 mSec    Memory Limit : 32768 KB

Problem Description

在一个平面内给定n个点,任意三个点不在同一条直线上,用这些点可以构成多少个平行四边形?一个点可以同时属于多个平行四边形。

Input

多组数据(<=10),处理到EOF。

每组数据第一行一个整数n(4<=n<=500)。接下来n行每行两个整数xi,yi(0<=xi,yi<=1e9),表示每个点的坐标。

Output

每组数据输出一个整数,表示用这些点能构成多少个平行四边形。

Sample Input

40 11 01 12 0

Sample Output

1

Source

福州大学第十三届程序设计竞赛

大体思路:

(1)这里,我们可以把任意两个点看为一组,然后把一组中的两个点用直线连起来,并找到它们的中点。如果有两组直线的中点一样(重合),则这两组中的四个点可以构成一个平行四边形。

(2)如何确定中点是否重合:若有四个点A,B,C,D.坐标分别为(x1,y1),(x2,y2),(x3,y3),(x4,y4)。若直线AC和BD的中点重合。则(x1+x3)/2=(x2+x4)/2,(y1+y3)/2=(y2+y4)/2;  化简得x1+x3=x2+x4,y1+y3=y2+y4。满足此条件时。ABCD四个点能构成一个平行四边形。



主要代码:


#include<iostream>
#include<algorithm>
#include<cstring>
#include<cstdio>
#include<string>
#include<cmath>
using namespace std;

struct ssr///使用结构数组,便于查找点的x,y坐标
{
    int x;
    int y;
} re[501],Map[501*501];///re数组是输入保存点的数据。
                        ///Map数组用来保存两个点组成的组的数据

bool cmp(ssr a,ssr b)///排序规则可更改,排序只是为了方便比较。
{
    if(a.x==b.x)
    {
        return a.y<b.y;
    }
    else
    {
        return a.x<b.x;
    }
}

int main()
{
    int n;
    while(cin>>n)
    {
        for(int i=0; i<n; i++)
        {
            scanf("%d %d",&re[i].x,&re[i].y);///输入部分,没啥好说的
        }

        int flag=0;

        for(int i=0; i<n-1; i++)
        {
            for(int j=i+1; j<n; j++)///把每两个点都组和一次
            {
                Map[flag].x=re[i].x+re[j].x;///计算出所有可能组的x和y的和的大小
                Map[flag].y=re[i].y+re[j].y;
                flag++;
            }
        }

        sort(Map,Map+flag,cmp);///排序后方便下面的比较

        int sum1=0;///sum1是中点相同的组的数量
        
        int sum2=0;///sum2是可组成平行四边形的数量

        for(int i=0;i<flag;i++)
        {
            if(Map[i].x==Map[i-1].x &&Map[i].y==Map[i-1].y)///相当于验证公式x1+x3=x2+x4,y1+y3=y2+y4;若相等,说明这两组的四个点可以组成平行四边形
            {
                sum1++;
            }
            else
            {
                sum2+=((1+sum1)*sum1)/2;///(稍后解释)
                sum1=0;
            }
        }
        printf("%d\n",sum2);

    }
    return 0;
}

其中
 sum2+=((1+sum1)*sum1)/2;

可以这样解释。如果有两个组1,2;可以组成的平行四边形有12。一个

                            如果有三个组1,2,3;可以组成的平行四边形有12,13,23。三个

                            如果有四个组1,2,3,4;可以组成的平行四边形有12,13,14,23,24,34。六个


满足递增数列1+2+3+4+5........

求和公式((n+1)*n)/2


最后全加到sum2上即可


                              





评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值