POJ 2826 || an easy problem ?!(未AC,呵呵~

微笑今日未AC,来日再战,头脑混沌。

#include<cstdio>
#include<cmath>
#include<algorithm>
using namespace std;
const double eps = 1e-8;
int dcmp( double x )
{
    if( fabs(x)<eps)
        return 0;
    return x < 0 ? -1: 1;
}

//================= 点结构 ===============
struct pnode
{
    double x,y;
    pnode( double a=0.0,double b=0.0):x(a),y(b){}

    // X乘重载
    double operator ^ (const pnode &b)const
    {
        return x*b.y - b.x*y;
    }

    pnode operator - ( const pnode &b)const
    {
        return pnode( x-b.x,    y-b.y);
    }

    pnode operator * (const double p)const
    {
        return pnode( x*p,   y*p );
    }

    pnode operator + (const pnode&b)const
    {
        return pnode( x+b.x, y+b.y );
    }

    bool operator == (const pnode&b)const
    {
        return dcmp( x-b.x )== 0 && dcmp( y-b.y )==0;
    }

    bool operator < (const pnode&b)const
    {
        return x < b.x || ( dcmp( x-b.x )==0 && y<b.y );
    }

    bool operator > (const pnode&b)const
    {
        return x > b.x || ( dcmp( x-b.x )==0 && y>b.y );
    }
};
//================ 线结构 ==============
typedef pnode myvec;
struct pline
{
    pnode st,ed;//st:起始点 ed:终点
    myvec vec;//向量
    pline(){}

    pline(pnode a,pnode b):st(a),ed(b)
    {
        vec = pnode(b-a);
    }
    void pread()
    {
        scanf("%lf %lf %lf %lf",&st.x,&st.y,&ed.x,&ed.y);
        if( ed.y > st.y)
            swap(st,ed);
        vec = pnode(ed-st);
    }
};

double cross( pnode p0,pnode p1,pnode p2)
{
    return (p1-p0) ^ (p2-p0);
}
double cross(pline a,pline b)
{
    return (a.ed-a.st)^(b.ed-b.st);
}

/*
    点乘:
        dot(v,w) == 二者长度乘积再乘上他们夹角的余弦
        夹角:从 v 到 w 逆时针旋转的角
*/
double dot( myvec v,myvec w)
{
    return v.x*w.x + v.y*w.y;
}
bool seg_inter_seg(pline a,pline b)
{

    return
        max( a.st.x, a.ed.x) >=  min( b.st.x, b.ed.x)
    &&
        max( b.st.x, b.ed.x) >=  min( a.st.x, a.ed.x)
    &&
        max( a.st.y, a.ed.y) >=  min( b.st.y, b.ed.y)
    &&
        max( b.st.y, b.ed.y) >=  min( a.st.y, a.ed.y)
    &&//以上端点判断
        dcmp(cross( a.st, a.ed, b.st ))*dcmp(cross( a.st, a.ed, b.ed ))<=0
    &&  dcmp(cross( b.st, b.ed, a.st ))*dcmp(cross( b.st, b.ed, a.ed ))<=0;
}
pnode get_line_inter_point(pline v,pline w)
{
    pline u (w.st,v.st);
    double t = cross( w,u )/cross(v,w);
    return v.st + (v.ed-v.st) * t;
}
bool seg_inter_line(pline line,pline seg)
{
    return ( dcmp( cross( seg.st,line.st,line.ed ) ) * dcmp( cross( seg.ed,line.st,line.ed) ) )<=0;
}
int check(pline a,pline b,pnode &p1,pnode &p2)
{
    pnode getit;
    pline ay (a.st,pnode(a.st.x+100,a.st.y));
    pline by (b.st,pnode(b.st.x+100,a.st.y));
    if( seg_inter_line(ay,b))
    {
        pline ax(a.st,pnode(a.st.x,10000 ));
        if( seg_inter_seg(ax,b))
            return 0;
        p1 = get_line_inter_point(ay,b);
        p2 = a.st;
        return 1;
    }
    if( seg_inter_line(by,a))
    {
        pline bx(b.st,pnode(b.st.x,10000 ));
        if( seg_inter_seg(bx,a))
            return 0;
        p1 = get_line_inter_point(by,a);
        p2 = b.st;
        return 1;
    }
    return 0;
}

pline a,b;
pline yl (pnode(0,0),pnode(0,100));
int main()
{
    int cas;
    scanf("%d",&cas);
    while( cas-- )
    {
        a.pread();
        b.pread();
        if( dcmp ( cross(a,b)) == 0 || dcmp(dot(yl.vec,a.vec))==0 || dcmp(dot(yl.vec,b.vec))==0 )
        {
            puts("0.00");
            //puts("1");
            continue;
        }
        pnode p = get_line_inter_point(a,b),p1,p2;
        int s = check(a,b,p1,p2);
        if( s==0 )
        {
            puts("0.00");
            //puts("2");
            continue;
        }
        double area = fabs ( cross(p,p1,p2)*0.5 );
        printf("%0.2f\n",area);

    }
    return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值