hdu 1558 判断线段相交 + 并查集

来源:互联网 发布:appstore没法下载软件 编辑:程序博客网 时间:2024/05/17 03:55
#include<cstdio>#include<iostream>using namespace std;int father[10008];int find(int x){    if(x == father[x])return x;    return father[x] = find(father[x]);}int merge(int a,int b){    int G = find(a);    int H = find(b);    if(G<H)        father[G] = H;    else        father[H] = G;}double fun(double x1,double y1,double x2,double y2){    return x1 * y2 - x2 * y1;}bool judge(double x1,double y1,double x2,double y2,double a,double a1,double b,double b1) // 判断线段相交{    double s= x2 - x1,s1 = y2 - y1;    double d1 = fun(s, s1, a-x1, a1-y1);    double d2 = fun(s, s1, b-x1, b1-y1);    s = b - a;    s1 = b1 - a1;    double d3 = fun(x1-a,y1-a1,s,s1);    double d4 = fun(x2-a,y2-a1,s,s1);   // cout<<d1 * d2<<" " << d3 * d4 <<endl;    if(d1 * d2 <= 0 && d3 * d4 <= 0)return true;    return false;}struct Node{    double x1,x2,y1,y2;}a[100008];int main(){    int n,m;    int icase;    char s[10];    double x1,x2,y1,y2;    scanf("%d",&icase);    while(icase --)    {        int k = 1;        scanf("%d",&n);        for(int i=1;i<=n;i++)        father[i] = i;        for(int i=1;i<=n;i++)        {            cin>>s;            if(s[0] == 'P'){            cin>>a[k].x1>>a[k].y1>>a[k].x2>>a[k].y2;            for(int j=1;j<k;j++)                if(judge(a[k].x1,a[k].y1,a[k].x2,a[k].y2,a[j].x1,a[j].y1,a[j].x2,a[j].y2)){                    merge(k,j);                }                k++;            }            else            {                int sum = 0;                cin>>m;                int x = find(m);                for(int i=1;i<=n;i++)                {                    if(x == find(i))                    {                        sum++;                    }                }                cout<<sum<<endl;            }        }        if(icase>0)puts("");    }}

0 0
原创粉丝点击