【Codevs1041】Car的旅行路线 Floyd 简单几何 (9/1000)

来源:互联网 发布:百度大数据分析工具 编辑:程序博客网 时间:2024/06/04 20:09

Description

又到暑假了,住在城市A的Car想和朋友一起去城市B旅游。她知道每个城市都有四个飞机场,分别位于一个矩形的四个顶点上,同一个城市中两个机场之间有一条笔直的高速铁路,第I个城市中高速铁路了的单位里程价格为Ti,任意两个不同城市的机场之间均有航线,所有航线单位里程的价格均为t。
那么Car应如何安排到城市B的路线才能尽可能的节省花费呢?她发现这并不是一个简单的问题,于是她来向你请教。
任务
找出一条从城市A到B的旅游路线,出发和到达城市中的机场可以任意选取,要求总的花费最少。

Input

第一行为一个正整数n(0<=n<=10),表示有n组测试数据。
每组的第一行有四个正整数s,t,A,B。
S(0 < S <= 100)表示城市的个数,t表示飞机单位里程的价格,A,B分别为城市A,B的序号(1<=A,B<=S)。
接下来有S行,其中第I行均有7个正整数xi1,yi1,xi2,yi2,xi3,yi3,Ti,这当中的(xi1,yi1),(xi2,yi2),(xi3,yi3) 分别是第I个城市中任意三个机场的坐标,Ti为第I个城市高速铁路单位里程的价格。

Output

共有n行,每行一个数据对应测试数据。

Sample Input

1
3 10 1 3
1 1 1 3 3 1 30
2 5 7 4 5 2 1
8 6 8 8 11 6 3

Sample Output

47.5

又是很明显一道题,求一座城市的四个点到另一个城市的四个点的最短距离,这题有一个小trick,就是添加一个虚拟的起点和一个虚拟的终点,这个虚拟的起点到起点城市的距离都为0,虚拟终点到终点四个城市的距离也都为0,跑一遍Dijkstra就可以了,但是,由于数据量很小。。直接Floyd就好了。
这题还有一个地方需要注意的是,知道矩形的三个点如何用求出第四个点(好问题),答案是用大边对大角,找到最大的边,然后就可以算出第四个点。
最后,molokai配色实在是太好看了,csdn的markdown代码太丑了。

#include<cstdio>#include<cstring>#include<cmath>#include<iostream>#include<algorithm>using namespace std;const int N=100+10;const int INF=0x3f3f3f3f;int n,s,t,A,B,T;int x[N][4],y[N][4];double d1,d2,d3,ans;double a[4*N][4*N];double dist(int x1,int y1,int x2,int y2){    return sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));}int main(){    //freopen("in.txt","r",stdin);    //freopen("out.txt","w",stdout);    cin>>n;    while(n--){        cin>>s>>t>>A>>B;        for(int i=0;i<s;i++){            for(int j=0;j<3;j++){                cin>>x[i][j]>>y[i][j];            }            cin>>T;            d1=dist(x[i][0],y[i][0],x[i][1],y[i][1]);            d2=dist(x[i][0],y[i][0],x[i][2],y[i][2]);            d3=dist(x[i][1],y[i][1],x[i][2],y[i][2]);            if (d1>=d2&&d1>=d3) {x[i][3]=x[i][0]+x[i][1]-x[i][2];y[i][3]=y[i][0]+y[i][1]-y[i][2];}            if (d2>=d1&&d2>=d3) {x[i][3]=x[i][0]+x[i][2]-x[i][1];y[i][3]=y[i][0]+y[i][2]-y[i][1];}            if (d3>=d1&&d3>=d2) {x[i][3]=x[i][1]+x[i][2]-x[i][0];y[i][3]=y[i][1]+y[i][2]-y[i][0];}            for(int j=0;j<4;j++){                for(int k=0;k<4;k++){                    if (j==k){                            a[4*i+j][4*i+k]=a[4*i+k][4*i+j]=0;                            continue;                    }                    a[4*i+j][4*i+k]=T*dist(x[i][j],y[i][j],x[i][k],y[i][k]);                    a[4*i+k][4*i+j]=T*dist(x[i][j],y[i][j],x[i][k],y[i][k]);                }            }        }        for(int i=0;i<s;i++){            for(int j=0;j<s;j++){                if (i!=j){                    for(int k=0;k<4;k++){                        for(int L=0;L<4;L++){                            a[4*i+k][4*j+L]=t*dist(x[i][k],y[i][k],x[j][L],y[j][L]);                            a[4*j+L][4*i+k]=t*dist(x[i][k],y[i][k],x[j][L],y[j][L]);                        }                    }                }            }        }        ans=INF;        for(int k=0;k<4*s;k++){            for(int i=0;i<4*s;i++){                for(int j=0;j<4*s;j++){                    a[i][j]=min(a[i][j],a[i][k]+a[k][j]);                }            }        }        for(int i=0;i<4;i++){            for(int j=0;j<4;j++){                ans=min(ans,a[4*(A-1)+i][4*(B-1)+j]);            }        }        printf("%.1f\n",ans);    }    return 0;}
原创粉丝点击