POJ2398计算几何

http://poj.org/problem?id=2398

题意:和POJ2318基本输入一样,但有一些改变。1.输入的线没按着从小到大的顺序,所以要先排序。2.输出要的是有1~m个点之间有多少个区间。例:有5条线,分成区域0,区域1,区域2,区域3,区域4,区域5.分别有2,1,3,5,4,0个点,所以输出就是1:1  2:1  3:1  4:1  5:1  ,再有就是看网上说用int会爆,所以改了一下范围。

AC代码:

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<algorithm>
using namespace std;
struct point
{
    __int64 x,y;
};
point a[5010],b[5010];//a是线上面的点,b是下面的点
int c[5010];
int d[5010];
int det(point a,point b,point g)//(g-b)*(a-b)
{
    return (g.x-b.x)*(a.y-b.y)-(a.x-b.x)*(g.y-b.y);
    //x1*y2-x2*y1
}
int main()
{
    int n,m;
    point g,g1,g2;
    int minn,maxn;
    while(scanf("%d",&n)!=EOF&&n)
    {
        scanf("%d",&m);
        scanf("%I64d%I64d%I64d%I64d",&g1.x,&g1.y,&g2.x,&g2.y);
        //面积边界
        for(int i=1; i<=n; i++)
        {
            scanf("%I64d%I64d",&a[i].x,&b[i].x);
        }
        a[n+1].x=g2.x;
        b[n+1].x=g2.x;
        a[0].x=g1.x;
        b[0].x=g1.x;
        for(int i=0; i<=n+1; i++)
        {
            a[i].y=g1.y;
            b[i].y=g2.y;
            c[i]=0;
        }
        for(int i=0;i<n-1;i++)
        {
            for(int j=1;j<n-i;j++)
            {
                if(a[j].x>a[j+1].x)
                {
                    swap(a[j],a[j+1]);
                    swap(b[j],b[j+1]);
                }
            }
        }
        //for(int i=1;i<=n;i++)
            //printf("%I64d %I64d ",a[i].x,b[i].x);
        n++;
        int mid,t;
        for(int i=1; i<=m; i++)
        {
            scanf("%I64d%I64d",&g.x,&g.y);
            minn=0;
            maxn=n;
            while(1)
            {
                mid=(minn+maxn)>>1;
                t=det(a[mid],b[mid],g);
                if(t<0)maxn=mid;
                else minn=mid;
                if(mid+1==maxn)break;
            }
            c[minn]++;
            //printf("%d   *\n",minn);
        }//二分查找,每次从中间的一根线判断
        printf("Box\n");
        memset(d,0,sizeof(d));
        for(int i=0;i<=n-1;i++)
            d[c[i]]++;
        for(int i=1;i<=m;i++)
            if(d[i]>0)printf("%d: %d\n",i,d[i]);
    }
    return 0;
}

 

posted @ 2013-08-07 18:42  拼搏今朝 努力奋进  阅读(207)  评论(0)    收藏  举报