洛谷P1119 災後重建

2022-08-13 23:48:17 字數 2542 閱讀 5817

b地區在**過後,所有村莊都造成了一定的損毀,而這場**卻沒對公路造成什麼影響。但是在村莊重建好之前,所有與未重建完成的村莊的公路均無法通車。換句話說,只有連線著兩個重建完成的村莊的公路才能通車,只能到達重建完成的村莊。

給出b地區的村莊數n,村莊編號從0到n-1,和所有m條公路的長度,公路是雙向的。並給出第i個村莊重建完成的時間t[i],你可以認為是同時開始重建並在第t[i]天重建完成,並且在當天即可通車。若t[i]為0則說明**未對此地區造成損壞,一開始就可以通車。之後有q個詢問(x, y, t),對於每個詢問你要回答在第t天,從村莊x到村莊y的最短路徑長度為多少。如果無法找到從x村莊到y村莊的路徑,經過若干個已重建完成的村莊,或者村莊x或村莊y在第t天仍未重建完成 ,則需要返回-1。

輸入格式:

輸入檔案rebuild.in的第一行包含兩個正整數n,m,表示了村莊的數目與公路的數量。

第二行包含n個非負整數t[0], t[1], …, t[n – 1],表示了每個村莊重建完成的時間,資料保證了t[0] ≤ t[1] ≤ … ≤ t[n – 1]。

接下來m行,每行3個非負整數i, j, w,w為不超過10000的正整數,表示了有一條連線村莊i與村莊j的道路,長度為w,保證i≠j,且對於任意一對村莊只會存在一條道路。

接下來一行也就是m+3行包含乙個正整數q,表示q個詢問。

接下來q行,每行3個非負整數x, y, t,詢問在第t天,從村莊x到村莊y的最短路徑長度為多少,資料保證了t是不下降的。

輸出格式:

輸出檔案rebuild.out包含q行,對每乙個詢問(x, y, t)輸出對應的答案,即在第t天,從村莊x到村莊y的最短路徑長度為多少。如果在第t天無法找到從x村莊到y村莊的路徑,經過若干個已重建完成的村莊,或者村莊x或村莊y在第t天仍未修復完成,則輸出-1。

輸入樣例#1:

4 5

1 2 3 4

0 2 1

2 3 1

3 1 2

2 1 4

0 3 5

42 0 2

0 1 2

0 1 3

0 1 4

輸出樣例#1:

-1-15

4

對於30%的資料,有n≤50;

對於30%的資料,有t[i] = 0,其中有20%的資料有t[i] = 0且n>50;

對於50%的資料,有q≤100;

對於100%的資料,有n≤200,m≤n*(n-1)/2,q≤50000,所有輸入資料涉及整數均不超過100000。

題解:這似乎是我各種蒙猜湊然後居然a了的題666

於是後來又看了看書才真正明白為什麼我的想法是對的

看到這道題後基本想法就是floyd,因為floyd的原理就是列舉不同的點做中轉點,然後將兩點間距離縮短

所以每到乙個時間點,就把到該時間點新修成的點作為中轉點將兩點間距離縮短

但後來我發現更新兩點距離時,從該中轉點出發到其餘點的最短距離需要先更新

(因為更新時dis[i][j]=min(dis[i][j],dis[i][k]+dis[k][j])嘛,如果dis[i][k]與dis[k][j]都不是當前最小值,那更新後的也不是最小值)

這是乙個偉大的猜想,這麼改過去就a了

------------------可愛的分割線------------------------

那麼這是為什麼呢?為什麼標準的floyd中就不用先更新dis[i][k]呢?

經過認真學習後發現,dis[i][k]在標準floyd中當k作為中轉點更新時,已被1~k-1作中轉點更新過了,是確定的只用1~k-1作中轉點後的最小值。

k又不用為dis[i][k]作中轉點,所以(完美)……

但是,我在題中用的演算法在k出現前,對於兩點的dis[i][j],只要兩點中有一點》=k,距離就為inf

也就是說,dis[i][k]是沒有被1~k-1更新過的。

故,需要先更新dis[i][k]

於是這次就瓦打正著了……複雜度也不高,n只有200,floyd妥妥的

看來學知識要學透,不要半半拉拉的。沒準這次矇對了,下次就沒有這樣好運氣了。

**:

1 #include2 #include3

#define inf 1000000007

4using

namespace

std;56

const

int maxn = 20005;7

struct

nodepool[2*maxn],*h[210

];11

intcnt;

12void addedge(int u,int v,int

len)

17int f[210][210],t[210

];18

intn;

1920

intmain()

2144

if(f[x][y]==inf) printf("

-1\n");

45else printf("

%d\n

",f[x][y]);46}

4748

return0;

49 }

view code

洛谷 P1119 災後重建

題目背景 b地區在 過後,所有村莊都造成了一定的損毀,而這場 卻沒對公路造成什麼影響。但是在村莊重建好之前,所有與未重建完成的村莊的公路均無法通車。換句話說,只有連線著兩個重建完成的村莊的公路才能通車,只能到達重建完成的村莊。題目描述 給出b地區的村莊數n,村莊編號從0到n 1,和所有m條公路的長度...

洛谷 P1119 災後重建

題目背景 b地區在 過後,所有村莊都造成了一定的損毀,而這場 卻沒對公路造成什麼影響。但是在村莊重建好之前,所有與未重建完成的村莊的公路均無法通車。換句話說,只有連線著兩個重建完成的村莊的公路才能通車,只能到達重建完成的村莊。題目描述 給出b地區的村莊數n,村莊編號從0到n 1,和所有m條公路的長度...

洛谷 P1119 災後重建

題目背景 b地區在 過後,所有村莊都造成了一定的損毀,而這場 卻沒對公路造成什麼影響。但是在村莊重建好之前,所有與未重建完成的村莊的公路均無法通車。換句話說,只有連線著兩個重建完成的村莊的公路才能通車,只能到達重建完成的村莊。題目描述 給出b地區的村莊數n,村莊編號從0到n 1,和所有m條公路的長度...