平面上有n条线段,询问某两条线段是否直接或间接相连。
才发现以前写的线段相交模板中没有处理共线但不相交的情况,现在加上了。
#include <iostream>
#include <cstring>
#include <cstdlib>
#include <cmath>
#include <vector>
#include <cstdio>
#include <algorithm>
#define N 10005
using namespace std;
typedef long long LL;
struct point
{
LL x , y;
point (LL x = 0 , LL y = 0): x(x) , y(y) {};
void input() {cin >> x >> y;}
bool operator < (const point& r) const{
if (x == r.x)
return y < r.y;
return x < r.x;}
bool operator == (const point& r) const{
return x == r.x && y == r.y;
}
};
point operator + (point a , point b) { return point(a.x + b.x , a.y + b.y);}
point operator - (point a , point b) { return point(a.x - b.x , a.y - b.y);}
LL Cross(point a , point b) {return a.x * b.y - a.y * b.x;}
double length(point a) {return sqrt(double(a.x) * a.x + double(a.y) * a.y);}
double dis(point a , point b) {return length(a - b);}
int dcmp(LL x) {return x == 0 ? 0 : x > 0 ? 1 : -1;}
bool SegmentI(point a1 , point a2 , point b1 , point b2)
{
LL c1 = Cross(a2 - a1 , b1 - a1) , c2 = Cross(a2 - a1 , b2 - a1),
c3 = Cross(b2 - b1 , a1 - b1) , c4 = Cross(b2 - b1 , a2 - b1);
if (!c1 && !c2 && !c3 && !c4)
{
point x = a2 < b2 ? a2 : b2;
point y = a1 < b1 ? b1 : a1;
return x == y || y < x;
}
return dcmp(c1) * dcmp(c2) <= 0 && dcmp(c3) * dcmp(c4) <= 0;
}
int n , f[N];
point a[N] , b[N];
int getf(int x) {return x == f[x] ? x : f[x] = getf(f[x]);}
void work()
{
int i , j;
for (i = 1 ; i <= n ; ++ i){
a[i].input() , b[i].input() , f[i] = i;
if (b[i] < a[i]) swap(a[i] , b[i]);
}
for (i = 1 ; i <= n ; ++ i)
for (j = i + 1 ; j <= n ; ++ j)
if (SegmentI(a[i] , b[i] , a[j] , b[j]))
f[getf(i)] = getf(j);
while (scanf("%d%d",&i,&j) , i || j)
puts(getf(i) == getf(j) ? "CONNECTED" : "NOT CONNECTED");
}
int main()
{
while(scanf("%d",&n) , n)
work();
return 0;
}