floyd算法是一種可以在o(v^3)求出一個圖中任意兩點最短路的算法
輸入:鄰接矩陣d
輸出:直接在d上面修改,每個元素d(i,j)代表點i到點j的最短路
這個算法的代碼非常短,一眼看上去非常暴力
for(int k=1;k<=v;k++)
for(int i=1;i<=v;i++)
for(int j=1;j<=v;j++)
d[i][j]=min(d[i][j],d[i][k]+d[k][j]);
思路大概是這樣:這裏用到了dp的方法,狀態轉移方程基本上就是
d[i][j]=min(d[i][j],d[i][k]+d[k][j]);
i,j,k用於遍歷所有節點,對於每一對節點i,j,若從i到j的直接距離比從i到k再到j的距離還要長,那麼根據最短路的統一思想,可以對它倆進行鬆弛,這個方程又同時是一個鬆弛。
然後每個點到自身的距離爲0(鄰接矩陣裏面就d[i][i]都初始化成0),作爲狀態轉移的一種終止條件。
總的來看,floyd算法就是dp的把整個圖鬆弛了一遍。
以hdu1596
find the safest road
爲例這個題裏面換湯不換藥的把值換成了0~1區間裏面的浮點數,最短路換成了路上值的乘積,稍作修改即可、
#include <bits/stdc++.h>
using namespace std;
const int maxn=1005;
float d[maxn][maxn];
int v;
void init()
{
for(int i=1;i<=v;i++)
{
for(int j=1;j<=v;j++)
{
scanf("%f ",&d[i][j]);
}
}
}
int main()
{
while(cin>>v)
{
init();
for(int k=1;k<=v;k++)
for(int i=1;i<=v;i++)
for(int j=1;j<=v;j++)
d[i][j]=max(d[i][j],d[i][k]*d[k][j]);
int c,c1,c2;
cin>>c;
while(c--)
{
cin>>c1>>c2;
if(d[c1][c2]==0)cout<<"What a pity!"<<endl;
else printf("%.3f\n",d[c1][c2]);
}
}
return 0;
}