http://poj.org/problem?id=2653
Time Limit: 3000MS | Memory Limit: 65536K | |
Total Submissions: 11638 | Accepted: 4390 |
Description
Input
Output
Sample Input
5 1 1 4 2 2 3 3 1 1 -2.0 8 4 1 4 8 2 3 3 6 -2.0 3 0 0 1 1 1 0 2 1 2 0 3 1 0
Sample Output
Top sticks: 2, 4, 5. Top sticks: 1, 2, 3.
题意:
在一个平面扔线段,问最后那些线段上没有线段压着,并输出这些线段
思路:
把每条线段与比它后扔下的线段判断是否相交,相交这这条线段上面还被线段压着,这时候就可以判断下一条线段了。
AC代码
#include <stdio.h> #include <string.h> #define MAXN 100000 #define max(a,b) (a>b?a:b) #define min(a,b) (a<b?a:b) int ans[MAXN+100]; typedef struct { double x,y; }point; point arr1[MAXN+100]; point arr2[MAXN+100]; double direction(point p1,point p3,point p4)//向量p3p1和向量p3p4的叉乘 { return (p1.x-p3.x)*(p4.y-p3.y)-((p4.x-p3.x))*(p1.y-p3.y); } bool judge(point p1,point p2,point p3,point p4) { double d1=direction(p1,p3,p4); double d2=direction(p2,p3,p4); double d3=direction(p3,p1,p2); double d4=direction(p4,p1,p2); if(d1*d2<=0&&d3*d4<=0) return 1; else return 0; } bool quickTest(point p1,point p2,point p3,point p4)//快速排斥实验 { if(min(p1.x,p2.x)<=max(p3.x,p4.x) &&min(p3.x,p4.x)<=max(p1.x,p2.x) &&min(p1.y,p2.y)<=max(p3.y,p4.y) &&min(p3.y,p4.y)<=max(p1.y,p2.y)) { return judge(p1,p2,p3,p4); } else return 0; } int main() { int N; bool flag[MAXN+100]; while(~scanf("%d",&N),N) { memset(flag,0,sizeof(flag));//表示第i条直线上方是否存在直线 for(int i=1;i<=N;i++) { scanf("%lf%lf%lf%lf",&arr1[i].x,&arr1[i].y,&arr2[i].x,&arr2[i].y); } for(int i=1;i<=N;++i) { for(int j=i+1;j<=N;++j) { if(judge(arr1[i],arr2[i],arr1[j],arr2[j])) { flag[i]=1; break;//没这个绝对超时 } } } printf("Top sticks: "); int j=0; for(int i=1;i<=N;++i) { if(!flag[i]) ans[j++]=i; } for(int i=0;i<j-1;++i) printf("%d, ",ans[i]); printf("%d.\n",ans[j-1]); } return 0; }