给出平面上两条线段的两个端点,判断这两条线段是否相交(有一个公共点或有部分重合认为相交)。 如果相交,输出"Yes",否则输出"No"。
Input
第1行:一个数T,表示输入的测试数量(1 <= T <= 1000) 第2 - T + 1行:每行8个数,x1,y1,x2,y2,x3,y3,x4,y4。(-10^8 <= xi, yi <= 10^8) (直线1的两个端点为x1,y1 | x2, y2,直线2的两个端点为x3,y3 | x4, y4)
Output
输出共T行,如果相交输出"Yes",否则输出"No"。
Input示例
2
1 2 2 1 0 0 2 2
-1 1 1 1 0 0 1 -1
Output示例
Yes
No
//线段相交模板题,学习了判断线段相交后,竟然debug一下午,因为我用的 long long ,
算完叉积后,相乘超过数据范围了,会出现错误,但如果使用的是double,超数据范围也不会改变符号,所以答案依旧是对的。。。
几何问题,这篇博客不错,几何
double:
1 #include <bits/stdc++.h> 2 using namespace std; 3 #define LL long long 4 #define eps 1e-8 5 #define MOD 1000000007 6 #define MX 1005 7 /* 8 判断P1P2跨立Q1Q2的依据是: 9 ( P1 - Q1 ) × ( Q2 - Q1 ) * ( Q2 - Q1 ) × ( P2 - Q1 ) ≥ 0 10 判断Q1Q2跨立P1P2的依据是: 11 ( Q1 - P1 ) × ( P2 - P1 ) * ( P2 - P1 ) × ( Q2 - P1 ) ≥ 0 12 */ 13 struct Point 14 { 15 double x,y; 16 Point(){} 17 Point(double _x,double _y){x=_x;y=_y;} 18 Point operator - (Point b)const{ 19 return Point(x-b.x,y-b.y); 20 } 21 double operator ^ (Point b)const{ 22 return x*b.y-b.x*y; 23 } 24 }pt[5]; 25 26 LL cha(int p1,int p2,int q1,int q2) 27 { 28 Point sa, sb, sc; 29 sa = pt[p1]-pt[q1]; 30 sb = pt[q2]-pt[q1]; 31 sc = pt[p2]-pt[q1]; 32 if ((sa^sb)*(sb^sc)<0) return 0; 33 return 1; 34 } 35 36 int main() 37 { 38 int T; 39 scanf("%d",&T); 40 while (T--) 41 { 42 for (int i=1;i<=4;i++) 43 scanf("%lf%lf",&pt[i].x,&pt[i].y); 44 if (cha(1,2,3,4)&&cha(3,4,1,2)) 45 printf("Yes "); 46 else 47 printf("No "); 48 } 49 return 0; 50 }
long long:
1 #include <bits/stdc++.h> 2 using namespace std; 3 #define LL long long 4 #define MOD 1000000007 5 #define MX 1005 6 struct Point 7 { 8 LL x,y; 9 Point(){} 10 Point(LL _x,LL _y){x=_x;y=_y;} 11 Point operator - (Point b)const{ 12 return Point(x-b.x,y-b.y); 13 } 14 LL operator ^ (Point b)const{ 15 return x*b.y-b.x*y; 16 } 17 }pt[5]; 18 19 LL cha(int p1,int p2,int q1,int q2) 20 { 21 Point sa, sb, sc; 22 sa = pt[p1]-pt[q1]; 23 sb = pt[q2]-pt[q1]; 24 sc = pt[p2]-pt[q1]; 25 LL c1 = sa^sb; 26 LL c2 = sb^sc; 27 if (c1>0&&c2>0) return 1; 28 if (c1<0&&c2<0) return 1; 29 if (c1==0||c2==0) return 1; 30 return 0; 31 } 32 33 int main() 34 { 35 int T; 36 scanf("%d",&T); 37 while (T--) 38 { 39 for (int i=1;i<=4;i++) 40 scanf("%lld%lld",&pt[i].x,&pt[i].y); 41 if (cha(1,2,3,4)&&cha(3,4,1,2)) 42 printf("Yes "); 43 else 44 printf("No "); 45 } 46 return 0; 47 }