郵票問題詳細題解 簡單dp

2021-10-06 03:55:30 字數 1968 閱讀 2697

已知乙個 n 枚郵票的面值集合(如,)和乙個上限 k —— 表示信封上能夠貼 k 張郵票。計算從 1 到 m 的最大連續可貼出的郵資。

例如,假設有 1 分和 3 分的郵票;你最多可以貼 5 張郵票。很容易貼出 1 到 5 分的郵資(用 1 分郵票貼就行了),接下來的郵資也不難:

6 = 3 + 3

7 = 3 + 3 + 1

8 = 3 + 3 + 1 + 1

9 = 3 + 3 + 3

10 = 3 + 3 + 3 + 1

11 = 3 + 3 + 3 + 1 + 1

12 = 3 + 3 + 3 + 3

13 = 3 + 3 + 3 + 3 + 1

然而,使用 5 枚 1 分或者 3 分的郵票根本不可能貼出 14 分的郵資。因此,對於這兩種郵票的集合和上限 k=5,答案是 m=13。

我們先給出將其看為多重集組合數來解得場景,不同之處在於,這裡限制了郵票使用的最大數目。我們使用兩個陣列

d p[

i],c

nt[i

]dp[i],cnt[i]

dp[i],

cnt[

i]表示使用最少cnt

[i

]cnt[i]

cnt[i]

個郵票就能拼湊出大小為i

ii的郵資,那麼動態規劃的過程分為三步

for

(int i =

1; i <= n; i++

)cin >> a[i]

;sort

(a +

1, a + n)

; dp[0]

=1; ll sum = k * a[n]

, maxj =0;

//最多能湊成的郵資

for(

int i =

1; i <= n; i++

)else dp[j + k * a[i]]=

1, cnt[j + k * a[i]

]= cnt[j]

+ k;}}

maxj = k * a[i]

;}

不幸的是,多重集組合數經常面臨著tle的危險,上面也不例外,只能拿80分,看了大佬的題解之後發現自己是乙個zz,其實只需要很簡單得轉換,我們就能拿下這道題,

注意看題,題目求得是從1開始得最長連續序列,因此我們只需要從i=0不斷向上搜尋,直到有乙個i不能拼湊出來,就得到了最長連續序列

最重要的部分只有4行,dp[

i]

dp[i]

dp[i

]是我們拼湊出i

ii郵資使用的最少郵票數目,dp得過程其實就是不斷更新最小郵票數目得過程,在滿足數目要求dp[

i]

<=k

dp[i]<=k

dp[i

]<=k

時,我們先將dp[

i+1]

dp[i+1]

dp[i+1

]設定為inf,然後遍歷每一種郵票,確保郵票得價值小於當前得i

ii(注意這裡要保證a從小到大排列),然後再滿足上述條件得情況下,使得dp[

i]

dp[i]

dp[i

]總是最小得

while

(dp[i]

<= k)

#define ll int

#define inf 0x3f3f3f3f

#define max 55

#define vec vector

#define p pair

//dp[j]:湊出j需要的最小郵票數目

int k, n, a[max]

, dp[

2000005];

intmain()

cout << i -

1<< endl;

}}

有趣的DP 郵票問題

題目描述 給定乙個信封,最多隻允許貼上n n 100 張郵票,我們現在有m m 100 種郵票,面值分別為 x1,x2 xm xi 255為正整數 並假設各種郵票都有足夠多張。要求計算所能獲得的郵資最大範圍。即求最大值max,使1 max之間的每乙個郵資都能得到。例如 n 4,有2種郵票,面值分別為...

簡單環(狀壓 dp,詳細注釋)

參考部落格 牛客網 wannafly挑戰賽17 c 簡單環 狀壓dp 題目描述 給定一張n個點m條邊的無向圖,求出圖中所有簡單環的數量。簡單環 簡單環又稱簡單迴路,圖的頂點序列中,除了第乙個頂點和最後乙個頂點相同外,其餘頂點不重複出現的迴路叫簡單迴路。或者說,若通路或迴路不重複地包含相同的邊,則它是...

DP 經典問題解析

解決dp 動態規劃 問題是需要思維訓練的,下面列舉了四個經典的dp問題和解析,希望對大家有幫助。題目比較長,在此略去了,可以從網上搜到具體描述。一 最長單調遞增子串行問題 遞減同理 1 用乙個陣列b n 記錄以a i 結尾的最長單調遞增子串行的長度 2 b i max 1,b 0 1 3 序列a的最...