1. 程式人生 > >HDU1596 find the safest road

HDU1596 find the safest road

find the safest road

  XX星球有很多城市,每個城市之間有一條或多條飛行通道,但是並不是所有的路都是很安全的,每一條路有一個安全係數s,s是在 0 和 1 間的實數(包括0,1),一條從u 到 v 的通道P 的安全度為Safe(P) = s(e1)*s(e2)…*s(ek) e1,e2,ek是P 上的邊 ,現在8600 想出去旅遊,面對這這麼多的路,他想找一條最安全的路。但是8600 的數學不好,想請你幫忙 ^_^。

Input

  輸入包括多個測試例項,每個例項包括: 
  第一行:n。n表示城市的個數n<=1000; 
  接著是一個n*n的矩陣表示兩個城市之間的安全係數,(0可以理解為那兩個城市之間沒有直接的通道) 接著是Q個8600要旅遊的路線,每行有兩個數字,表示8600所在的城市和要去的城市。

Output

  如果86無法達到他的目的地,輸出"What a pity!", 其他的輸出這兩個城市之間的最安全道路的安全係數,保留三位小數。

Sample Input

3
1 0.5 0.5
0.5 1 0.4
0.5 0.4 1
3
1 2
2 3
1 3

Sample Output

0.500
0.400
0.500

解題思路:
  本題有多組測試資料,每組給出城市的數量與其安全係數鄰接矩陣,之後給出旅遊線路數量與每條線路的起點與終點。

  本題幾乎是dijkstra模板題,本題是使用dijkstra尋找最大安全係數,注意對安全係數是進行乘法運算。

  用一個double陣列safety儲存從起點到所有城市的最大安全係數,一個布林陣列記錄是否固定對應城市的最大安全係數。初始狀態將到所有城市的安全係數視為0,從起點開始標記,記錄起點到自己的安全係數為1並將其固定,之後每次找到並固定到達起點安全係數最大的城市,固定一個城市後檢視以該城市為媒介是否能使還沒有固定的城市到達起點的安全係數增高,如果能優化,將優化後的記入該城市對應的safety中。

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 const int maxn = 1e3+10;
 4 int n, q, s;
 5 double G[maxn][maxn];   //G記錄鄰接矩陣
 6 double safety[maxn];    //safety記錄起點到各城市的最大安全係數
 7 bool vis[maxn] = {false};   //vis記錄城市最大安全係數是否已經固定
 8 
 9 void dijkstra(int s){   //傳入起點
10     memset(safety, 0, sizeof
(safety)); //初始化起點到所有城市的最大安全係數為0 11 memset(vis, false, sizeof(vis)); //所有城市都為未固定狀態 12 safety[s] = 1.0; //起點到自己的最大安全係數為1 13 for(int i = 0; i < n; i++){ 14 //開始計算並固定城市最大安全係數,需要將每個城市都固定所以迴圈n次 15 int maxSafetyCity = -1; 16 double maxSafetyNum = -1; 17 for(int j = 0; j < n; j++){ //找到還沒有固定的城市中到起點安全係數最大的城市 18 if(!vis[j] && safety[j] > maxSafetyNum){ 19 maxSafetyCity = j; //maxSafeCity記錄還沒有固定的城市中到起點安全係數最大的城市 20 maxSafetyNum = safety[j]; //maxSafetyNum記錄當前最大安全係數 21 } 22 } 23 if(maxSafetyCity == -1){ //如果找不到符合條件的城市,證明其餘城市與起點不連通 24 return; 25 } 26 vis[maxSafetyCity] = true; //固定安全係數最大的城市 27 for(int j = 0; j < n; j++){ //尋找以該城市為媒介可以優化的城市 28 if(!vis[j] && G[maxSafetyCity][j] != 0 && G[maxSafetyCity][j] * safety[maxSafetyCity] > safety[j]){ 29 //可以優化的條件為,該城市沒有固定 30 //該城市與媒介城市連通 31 //從媒介城市到該城市的安全係數乘以媒介城市到起點的安全係數比不優化前該城市到達起點的安全係數高 32 safety[j] = safety[maxSafetyCity] * G[maxSafetyCity][j]; 33 //優化 34 } 35 } 36 } 37 } 38 int main() 39 { 40 while(scanf("%d", &n) != EOF){ //輸入城市數量 41 for(int i = 0; i < n; i++){ 42 for(int j = 0; j < n; j++){ 43 scanf("%lf", &G[i][j]); //輸入鄰接矩陣 44 } 45 } 46 scanf("%d", &q); //輸入旅行路線 47 int ed; 48 for(int i = 0; i < q; i++){ 49 scanf("%d%d", &s, &ed); //輸入起點與終點 50 dijkstra(s - 1); //計算起點到所有城市的最大安全係數 51 if(safety[ed - 1] != 0){ 52 printf("%.3f\n", safety[ed - 1]); //格式化輸出最大安全係數 53 }else{ 54 printf("What a pity!\n"); //不連通 55 } 56 } 57 } 58 return 0; 59 }