poj 1410 判断线段和矩形是否相交

来源:互联网 发布:java treeset 排序 编辑:程序博客网 时间:2024/04/27 17:12

题意:给定一条线段的两个端点,再给定矩形顶点的两个横坐标和两个总坐标(矩形的边与坐标轴平行)。求线段和矩形是否有公共点(矩形是实心的)

思路:首先题意确实比较容易出现歧义。需要注意两点:1、矩形是实心的(The rectangle consists of four straight lines and the area in between),所以如果线段完全在矩形内部也算相交;2、给定的矩形坐标并不是按照矩形的端点坐标给出的,而需要自行判断。

那么所需判断的就是给定线段和矩形四条边是否相交,如果不相交,再判断线段是否在矩形内部。

#include <stdio.h>#include <string.h>#define min(a,b) ((a)<(b)?(a):(b))#define max(a,b) ((a)>(b)?(a):(b))#define eps 1e-10typedef struct point{int x,y;}P;P p[4],s,t;int n,T;double multi(P a,P b,P c){return (b.x-a.x)*(c.y-a.y)-(b.y-a.y)*(c.x-a.x);}int inter(P x,P y,P s,P t){//判断线段xy和线段st是否相交double a,b,c,d;if(min(x.x,y.x)>max(s.x,t.x) || min(x.y,y.y)>max(s.y,t.y) ||min(s.x,t.x)>max(x.x,y.x) || min(s.y,t.y)>max(x.y,y.y))return 0;a = multi(x,y,s);b = multi(x,y,t);c = multi(s,t,x);d = multi(s,t,y);return a*b<eps && c*d<eps;}int in(P a){//判断点a是否在矩形内部return a.x>=p[0].x&&a.x<=p[2].x&&a.y>=p[0].y&&a.y<=p[2].y;}int main(){freopen("a.txt","r",stdin);scanf("%d",&T);while(T--){int i,j,flag=0;scanf("%d %d %d %d",&s.x,&s.y,&t.x,&t.y);scanf("%d %d %d %d",&p[0].x,&p[0].y,&p[2].x,&p[2].y);if(p[0].x > p[2].x){int temp = p[0].x;p[0].x = p[2].x;p[2].x = temp;}if(p[0].y > p[2].y){int temp = p[0].y;p[0].y = p[2].y;p[2].y = temp;}//使得p[0]存放矩形的左下点,p[2]存放右上点p[1].x = p[2].x;p[1].y = p[0].y;p[3].x = p[0].x;p[3].y = p[2].y;for(i = 0;i<4;i++)if(inter(p[i],p[(i+1)%4],s,t)){//分别判断线段和矩形边是否相交flag = 1;break;}if(!flag && (in(s) || in(t)))//判断线段端点是否在矩形内部flag = 1;if(flag)printf("T\n");elseprintf("F\n");}return 0;}


0 0
原创粉丝点击