1. 程式人生 > >bzoj 1061 志願者招募

bzoj 1061 志願者招募

這道題正確的解法是構造網路,求網路最小費用最大流,但是模型隱藏得較深,不易想到。構造網路是該題的關鍵,以下面一個例子說明構圖的方法和解釋。

例如一共需要4天,四天需要的人數依次是4,2,5,3。有5類志願者,如下表所示:

種類 1 2 3 4 5
時間 1-2 1-1 2-3 3-3 3-4
費用 3 4 3 5 6

設僱傭第i類志願者的人數為X[i],每個志願者的費用為V[i],第j天僱傭的人數為P[j],則每天的僱傭人數應滿足一個不等式,如上表所述,可以列出

P[1] = X[1] + X[2] >= 4

P[2] = X[1] + X[3] >= 2

P[3] = X[3] + X[4] +X[5] >= 5

P[4] = X[5] >= 3

對於第i個不等式,新增輔助變數Y[i] (Y[i]>=0) ,可以使其變為等式

P[1] = X[1] + X[2] - Y[1] = 4

P[2] = X[1] + X[3] - Y[2] = 2

P[3] = X[3] + X[4] +X[5] - Y[3] = 5

P[4] = X[5] - Y[4] = 3

在上述四個等式上下新增P[0]=0,P[5]=0,每次用下邊的式子減去上邊的式子,得出

① P[1] - P[0] = X[1] + X[2] - Y[1] = 4

② P[2] - P[1] = X[3] - X[2] -Y[2] +Y[1] = -2

③ P[3] - P[2] = X[4] + X[5] - X[1] - Y[3] + Y[2] =3

④ P[4] - P[3] = - X[3] - X[4] + Y[3] - Y[4] = -2

⑤ P[5] - P[4] = - X[5] + Y[4] = -3

觀察發現,每個變數都在兩個式子中出現了,而且一次為正,一次為負。所有等式右邊和為0。接下來,根據上面五個等式構圖。

  • 每個等式為圖中一個頂點,新增源點S和匯點T。
  • 如果一個等式右邊為非負整數c,從源點S向該等式對應的頂點連線一條容量為c,權值為0的有向邊;如果一個等式右邊為負整數c,從該等式對應的頂點向匯點T連線一條容量為c,權值為0的有向邊。
  • 如果一個變數X[i]在第j個等式中出現為X[i],在第k個等式中出現為-X[i],從頂點j向頂點k連線一條容量為∞,權值為V[i]的有向邊。
  • 如果一個變數Y[i]在第j個等式中出現為Y[i],在第k個等式中出現為-Y[i],從頂點j向頂點k連線一條容量為∞,權值為0的有向邊。

構圖以後,求從源點S到匯點T的最小費用最大流,費用值就是結果。

根據上面的例子可以構造出如下網路,紅色的邊為每個變數X代表的邊,藍色的邊為每個變數Y代表的邊,邊的容量和權值標已經標出(藍色沒有標記,因為都是容量∞,權值0)。

noi_employee_1

在這個圖中求最小費用最大流,流量網路如下圖,每個紅色邊的流量就是對應的變數X的值。

noi_employee_2

所以,答案為43+23+3*6=36。

上面的方法很神奇得求出了結果,思考為什麼這樣構圖。我們將最後的五個等式進一步變形,得出以下結果

① - X[1] - X[2] + Y[1] + 4 = 0

② - X[3] + X[2] + Y[2] - Y[1] - 2 = 0

③ - X[4] - X[5] + X[1] + Y[3] - Y[2] + 3 = 0

④ X[3] + X[4] - Y[3] + Y[4] - 2 = 0

⑤ X[5] - Y[4] - 3 = 0

可以發現,每個等式左邊都是幾個變數和一個常數相加減,右邊都為0,恰好就像網路流中除了源點和匯點的頂點都滿足流量平衡。每個正的變數相當於流入該頂點的流量,負的變數相當於流出該頂點的流量,而正常數可以看作來自附加源點的流量,負的常數是流向附加匯點的流量。因此可以據此構造網路,求出從附加源到附加匯的網路最大流,即可滿足所有等式。而我們還要求noi_employee_3最小,所以要在X變數相對應的邊上加上權值,然後求最小費用最大流

我寫的是樸素的SPFA演算法求增廣路的最小費用流演算法,可以在題目時限內通過所有測試點。

在NOI的現場上,該題得分的平均分12.56,只有高逸涵大牛拿到了滿分。不能不說這是一道難題,難就難在抽象出問題的數學模型,設計有效的演算法。而資訊學競賽正朝著這個方向發展,數學建模將是解決問題的共同關鍵步驟。

建圖的話看看上面的圖就知道了,規律十分明顯。