題解
該題考察最短路問題,採用 dijkstra 演算法,並在其基礎上進行擴充套件。
首先是路徑列印,需要記錄該點具體由上乙個(哪乙個點)轉移過來的,用 $path$ 陣列記錄(具體在更新迴圈中)。
如上圖。
敲重點
關於如何求解路徑條數和對應最短路徑下的最多救援隊數量,我們先看下圖
設 $su[i]$ 表示從 $s$ (起點)到 $i$ 點最短距離救援隊數量的最大值,$dist[i]$ 表示從 $s$ (起點)到 $i$ 點的最短距離,採用鄰接矩陣 $g$ 儲存所有的邊,$num[i]$ 儲存 $s$(起點)到 $i$ 點最短路徑的條數。
滿足 dist[j] <= dist[t] + g[t][j] 的情況下,我們分兩種情況進行討論
1、dist[j] == dist[t] + g[t][j]
>則距 j 點對應的最短距離是不變的,此時數量對其取 max 即可。
>路徑很顯然增加 num[t](可由 t 擴充套件)。
2、dist[j]
>則需更新最短距離,由此路徑必定為經過 t 再經過由 t 到 j 的邊,此時的數量更新為 su[t] + c[j](c[j] 表示 j 點對應救援隊的數量)。
>路徑也必須更新至 t 對應的最短路徑的條數。
記得初始 num[s] = 1,即自己到自己的一條路徑。
#include #include#include
using
namespace
std;
const
int n = 510
;int
n, m, s, d, ans;
intg[n][n], dist[n], c[n], path[n], num[n], p[n];
intsu[n];
bool
st[n];
void
dijkstra()
}
st[t] = true
;
for (int j = 0; j < n; ++j)
}else}}
}int last =d;
while (last !=s)
p[ans++] =last;
cout
<< num[d] << "
"<< su[d] <
for (int i = ans - 1; i >= 0; --i)
else
}}int
main()
for (int i = 0; i < m; ++i)
//因為由 s 點出發
num[s] = 1
; dijkstra();
return0;
}
L2 001 緊急救援
這道題就是一道最短路 dijkstra演算法 將模板稍作修改就行了,就是再另外加乙個記錄路線條數的陣列 即當路的長度與下乙個需要判斷的 節點的長度相等時路線就相加 和乙個記錄每個節點在最短路基礎上的車的總數量的陣列,然後就ok了,如下 include include include define m...
L2 001 緊急救援
作為乙個城市的應急救援隊伍的負責人,你有一張特殊的全國地圖。在地圖上顯示有多個分散的城市和一些連線城市的快速道路。每個城市的救援隊數量和每一條連線兩個城市的快速道路長度都標在地圖上。當其他城市有緊急求助 給你的時候,你的任務是帶領你的救援隊盡快趕往事發地,同時,一路上召集盡可能多的救援隊。輸入格式 ...
L2 001 緊急救援
l2 001.緊急救援 作為乙個城市的應急救援隊伍的負責人,你有一張特殊的全國地圖。在地圖上顯示有多個分散的城市和一些連線城市的快速道路。每個城市的救援隊數量和每一條連線兩個城市的快速道路長度都標在地圖上。當其他城市有緊急求助 給你的時候,你的任務是帶領你的救援隊盡快趕往事發地,同時,一路上召集盡可...