描述 Description
在一个长宽均为10,入口出口分别为(0,5)、(10,5)的房间里,有几堵墙,每堵墙上有两个缺口,求入口到出口的最短路经。
输入格式 Input Format
第一排为n(n<=20),墙的数目。
接下来n排,每排5个实数x,a1,b1,a2,b2。
x表示墙的横坐标(所有墙都是竖直的),a1-b1和a2-b2之间为空缺。
a1、b1、a2、b2保持递增,x1-xn也是递增的。
输出格式 Output Format
输出最短距离,保留2位小数。
1 #include<iostream> 2 #include<math.h> 3 //#include<fstream> 4 #include<stdio.h> 5 using namespace std; 6 7 double d[25][5],y[25][5],x[25]; 8 int n; 9 10 int main() 11 { 12 int i,j,k,l; 13 cin>>n; 14 15 for(j=1;j<=4;++j) 16 {d[1][j]=0;x[1]=0;y[1][j]=5;} 17 18 for(i=2;i<=n+1;++i) 19 { 20 cin>>x[i]; 21 for(j=1;j<=4;++j) 22 cin>>y[i][j],d[i][j]=0xfffffff; 23 } 24 25 for(j=1;j<=4;++j) 26 {x[n+2]=10;y[n+2][j]=5;d[n+2][j]=0xfffffff;} 27 28 for(i=2;i<=n+2;++i) 29 { 30 for(j=1;j<=4;++j) 31 for(k=1;k<=4;++k) 32 d[i][j]=min(d[i][j],sqrt((x[i]-x[i-1])*(x[i]-x[i-1])+(y[i][j]-y[i-1][k])*(y[i][j]-y[i-1][k]))+d[i-1][k]); 33 } 34 35 int s,t; 36 for(i=3;i<=n+2;++i) 37 for(j=1;j<=4;++j) 38 for(k=i-2;k>=1;--k) 39 for(l=1;l<=4;++l) 40 { 41 for(t=1;t<=4;++t) 42 d[i][j]=min(d[i][j],sqrt((x[i]-x[i-1])*(x[i]-x[i-1])+(y[i][j]-y[i-1][t])*(y[i][j]-y[i-1][t]))+d[i-1][t]); 43 double kik=(y[i][j]-y[k][l]); 44 bool p=0; 45 for(t=k+1;t<=i-1;++t) 46 { 47 p=0; 48 for(s=1;s<=4;++s,++s) 49 { 50 double kit=(y[i][j]-y[t][s]); 51 double kit2=(y[i][j]-y[t][s+1]); 52 if(kik*(x[i]-x[t])<=kit*(x[i]-x[k])&&kik*(x[i]-x[t])>=kit2*(x[i]-x[k])) p=1; 53 } 54 if(p==0) break; 55 } 56 if(p==0) continue; 57 d[i][j]=min(d[i][j],d[k][l]+sqrt((x[i]-x[k])*(x[i]-x[k])+(y[i][j]-y[k][l])*(y[i][j]-y[k][l]))); 58 } 59 60 printf("%.2lf",d[n+2][1]); 61 cout<<endl; 62 return 0; 63 }