题意:扔n根棍,问最后没被压倒的根有哪些
典型的线段相交,
我原来的解法是每人一根就跟前边已有的判断压住则标记O(n^n)复杂度,tle了
后来看了看discuss,发现原来从后往前判断可大大降低时间复杂度,暴力也要注意思路啊!
#include <stdio.h>
#include <string.h>
#define SIZE 100010
typedef struct point{
double x,y;
}Point;
Point line[SIZE][2];
int top[SIZE];
/*- left ;+ right*/
double direction(Point p1,Point p2,Point p0)
{
return (p2.x-p1.x)*(p0.y-p1.y)-(p2.y-p1.y)*(p0.x-p1.x);
}
int insect(Point p1,Point p2,Point p3,Point p4)
{
double d1 = direction(p3,p4,p1);
double d2 = direction(p3,p4,p2);
double d3 = direction(p1,p2,p3);
double d4 = direction(p1,p2,p4);
return d1*d2<0 && d3*d4<0 ? 1 : 0;
}
int main()
{
int n,i,j;
while(1){
scanf("%d",&n);
if(n == 0) break;
for(i = 0; i < n; i++)
scanf("%lf%lf%lf%lf",&line[i][0].x,&line[i][0].y,&line[i][1].x,&line[i][1].y);
for(i = n-1; i >= 0; i--){ //从后往前枚举,否则tle
top[i] = 1;
for(j = n-1; j > i; j--)
if(insect(line[j][0],line[j][1],line[i][0],line[i][1])){
top[i] = 0;
break;
}
}
printf("Top sticks:");
for(i = 0; i < n;i++)
if(top[i]) {
printf(" %d",i+1);
break;
}
for(i++; i < n; i++)
if(top[i]) printf(", %d",i+1);
printf(".\n");
}
return 0;
}