Tyvj1098任務安排

2022-05-29 07:06:15 字數 1754 閱讀 9471

這篇講解部分已經整合進入 。**留在這裡。

n個任務排成乙個序列在一台機器上等待完成(順序不得改變),這n個任務被分成若干批,每批包含相鄰的若干任務。從時刻0開始,這些任務被分批加工,第i個任務單獨完成所需的時間是ti。在每批任務開始前,機器需要啟動時間s,而完成這批任務所需的時間是各個任務需要時間的總和(同一批任務將在同一時刻完成)。每個任務的費用是它的完成時刻乘以乙個費用係數fi。請確定乙個分組方案,使得總費用最小。

例如:s=1;t=;f=。如果分組方案是、、,則完成時間分別為,費用c=,總費用就是153。

5 

1 1 3

3 2

4 3

2 3

1 4

153
很顯然,由於順序不能改變,所以可以使用dp來求解。狀態是關鍵!下面給出兩個不同的方法,由於狀態不同,複雜度相去甚遠。

雖然時間就是金錢,但是這裡我們會把f值看作金錢,而時間看成金錢的單位。

費用s = t * f,顯然s = f+f+f...(t個f)。

所以時間t每增加k,即t

' = t+k,

那麼s' - s = kf。

我們便說:金錢又被收了k次。

這是一種最顯然的方法,即記錄下當前時間,在決策時直接使用sigma(time) * f獲取當前費用。不妨用dp[i][t]表示從t秒開始,完成任務i到n所需最小費用。不難得出dp方程:

dp[i][t] = min

k = i..n

邊界:dp[n+1][..] = 0

目標:dp[1][0]

順著剛才的思路,我們考慮每當乙個決策可能在未來產生消費時,就立刻預先支付這個價值。建議各位先深刻理解劉汝佳/黃亮黑書p151的最優二分檢索樹是如何推算出dp方程的。

分析問題: 每個任務的費用是它的完成時刻乘以乙個費用係數fi。不妨看成費用係數fi進行了連續加法,當前決策之前的每乙個決策每使時間過去了1,就要在當前費用中加上乙個fi;反過來,當前的決策每使時間增加k分鐘,或者如開頭所說收了k次錢,就會使它以及其後的每乙個任務的費用加上fi。正是這種化乘法為加法的思路,削去了冗餘的時間一維。由此得出dp方程:

dp[i]表示第i個到第n個任務所需的費用

dp[i] = min

其中 i ≤ j ≤ n

邊界是 dp[n+1]=0

目標是 dp[1]

深刻理解這個方程,會受益匪淺。

方程中可以看出,i是遞減的,無腦給出c++**

#include 

#include

using

namespace

std;

#define ll int64_t

ll dp[5005];

ll sumt[5005],sumf[5005];

int n,s;

int main()

for (int i=n; i>=1; i--)

}cout

<< dp[1] << endl;

return

0;}

Tyvj1098 任務安排

恕我懶 分析 本蒟蒻只想到了辣雞做法 f i,j 表示前j個任務分了i組,最少費用,f i,j min 發現這是o n 3 的,水不過去.於是腦洞大開想寫乙個二維的斜率優化.不知道為什麼一直wa了乙個點.於是去尋找正解,發現只需要開1維陣列就夠了,驚呆我了.用f i 表示從第i個任務開始做的最小費用...

TYVJ 1098 任務安排

n個任務排成乙個序列在一台機器上等待完成 順序不得改變 這n個任務被分成若干批,每批包含相鄰的若干任務。從時刻0開始,這些任務被分批加工,第i個任務單獨完成所需的時間是ti。在每批任務開始前,機器需要啟動時間s,而完成這批任務所需的時間是各個任務需要時間的總和 同一批任務將在同一時刻完成 每個任務的...

Tyoj1098 任務安排

n個任務排成乙個序列在一台機器上等待完成 順序不得改變 這n個任務被分成若干批,每批包含相鄰的若干任務。從時刻0開始,這些任務被分批加工,第i個任務單獨完成所需的時間是ti。在每批任務開始前,機器需要啟動時間s,而完成這批任務所需的時間是各個任務需要時間的總和 同一批任務將在同一時刻完成 每個任務的...