The Doors
题目链接:https://vjudge.net/problem/POJ-1556
题目:
思路:就是判断线段与线段是否相交,符合条件就加入图中,建完图后跑dij就行了,求最短路,,看了大神的。。
#include#include #include #include #include #define Max 105 #define eps 1e-8 #define Inf 0x7fffffff using namespace std; int head[Max],cnt; struct { int e; double w; int next; }edge[Max*Max]; struct Point { double x,y; }point[Max]; struct Seg { Point a,b; }seg[Max]; void add(int s,int e,double w) { edge[cnt].e=e; edge[cnt].w=w; edge[cnt].next=head[s]; head[s]=cnt++; } double distance(double x1,double y1,double x2,double y2) { return sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2)); } int dblcmp(double d) { if(fabs(d) return 0; return d>0?1:-1; } double det(double x1,double y1,double x2,double y2) { return x1*y2-x2*y1; } double cross(Point a,Point b,Point c) { return det(b.x-a.x,b.y-a.y,c.x-a.x,c.y-a.y); } int segcross(Point a,Point b,Point c,Point d) { return (dblcmp(cross(a,c,d))^dblcmp(cross(b,c,d)))==-2&& (dblcmp(cross(c,a,b))^dblcmp(cross(d,a,b)))==-2; } double spfa(int n) { int i,st,ed; bool visit[Max]; double dis[Max]; queue<int> q; memset(visit,false,sizeof(visit)); visit[0]=true; for(i=1;i<=n;i++) dis[i]=Inf*1.0; dis[0]=0; q.push(0); while(!q.empty()) { st=q.front(); q.pop(); visit[st]=false; for(i=head[st];i!=-1;i=edge[i].next) { ed=edge[i].e; if(dis[ed]>dis[st]+edge[i].w) { dis[ed]=dis[st]+edge[i].w; if(!visit[ed]) { visit[ed]=true; q.push(ed); } } } } return dis[n]; } int main() { //freopen("text","r",stdin); int i,j,k,n,t,p; bool flag; double x,y[6]; while(~scanf("%d",&n)) { if(n==-1) break; cnt=p=0; memset(head,-1,sizeof(head)); t=1; point[0].x=0.0;point[0].y=5.0; for(i=1;i<=n;i++) { scanf("%lf",&x); y[0]=0.0;y[5]=10.0; for(j=1;j<=4;j++) { scanf("%lf",&y[j]); point[++p].x=x; point[p].y=y[j]; } seg[t].a.x=x;seg[t].a.y=y[0]; seg[t].b.x=x;seg[t++].b.y=y[1]; seg[t].a.x=x;seg[t].a.y=y[2]; seg[t].b.x=x;seg[t++].b.y=y[3]; seg[t].a.x=x;seg[t].a.y=y[4]; seg[t].b.x=x;seg[t++].b.y=y[5]; } point[++p].x=10.0;point[p].y=5.0; for(i=0;i<=p;i++) for(j=i+1;j<=p;j++) { flag=true; for(k=1;k ) { if(point[i].x!=seg[k].a.x&&point[j].x!=seg[k].a.x&&segcross(point[i],point[j],seg[k].a,seg[k].b)) { flag=false; break; } } if(flag) add(i,j,distance(point[i].x,point[i].y,point[j].x,point[j].y)); } printf("%.2f\n",spfa(p)); } return 0; }