noip1999郵票面值設計
題目描述 description
給定乙個信封,最多隻允許貼上n張郵票,計算在給定k(n+k≤40)種郵票的情況下(假定所有的郵票數量都足夠),如何設計郵票的面值,能得到最大值max,使在1~max之間的每乙個郵資值都能得到。
例如,n=3,k=2,如果面值分別為1分、4分,則在1分~6分之間的每乙個郵資值都能得到(當然還有8分、9分和12分);如果面值分別為1分、3分,則在1分~7分之間的每乙個郵資值都能得到。可以驗證當n=3,k=2時,7分就是可以得到的連續的郵資最大值,所以max=7,面值分別為1分、3分。
輸入描述 input description
n和k輸出描述 output description
每種郵票的面值,連續最大能到的面值數。資料保證答案唯一。
樣例輸入 sample input
3 2樣例輸出 sample output
1 3max=7
這道題的做法是dfs+dp,整體的思路是:先搜出一種郵票面值組合方案,再用dp求出在這種方案下能組合出的最大的總面值
dps:沒什麼特殊的,需要注意的是,當前正在列舉的這個郵票的面值的下界是前乙個郵票的面值+1,上界是在還沒有這張郵票的時候,前面的郵票最大能組成多大的面值+1
dp:這是一位神犇的部落格裡看到的,f[i]表示用當前這些郵票,組合出i的面值,需要最少的郵票數,now陣列中存的是郵票的面值,則有f[i]=min+1(j=1...郵票數),乙個明顯的結論是f陣列一定是不下降的,所以
當發現f[i]>n時,i-1就是最大面值
**:
//noip1999 郵票面值設計 動態規劃+搜尋
#include #include #include #define inf 0x3f3f3f3f
using namespace std;
int max=-inf, size, n, k, f[500];
vectorans, now;
int update()
return i-1;
} i++; }}
void dfs(const int deep)
{ int m, i;
m=update();
for(i=now[now.size()-1]+1;i<=m+1;i++)
{ now.push_back(i);
update();
if(deep
NOIP1999 郵票面值設計
時間限制 1 sec 記憶體限制 64 mb 提交 131 解決 63 提交 狀態 我的提交 給定乙個信封,最多隻允許貼上n張郵票,計算在給定k n k 40 種郵票的情況下 假定所有的郵票數量都足夠 如何設計郵票的面值,能得到最大值max,使在1 max之間的每乙個郵資值都能得到。第1行 2個整數...
郵票面值設計(NOIP1999)
傳送門 怎麼講呢?挺有意思的 是一道dp和搜尋的結合。我們把數字從小到大依次列舉。用dp去計算當前的所得最大值。f i 表示湊成i面值所需的最小郵票數量。那麼小於等於n的,都是可以湊出來的。那麼最大值也就好求了。至於dp的上界,用幾個數的和就能解決。如下 include include includ...
NOIP1999 郵票面值設計
給定乙個信封,最多隻允許貼上n張郵票,計算在給定k種郵票的情況下 假定所有的郵票數量都足夠 如何設計郵票的面值,能得到最大max,使得1 max之間的每乙個郵資值都能得到。例如,n 3,k 2,如果面值分別為1分 4分,則在l分 6分之間的每乙個郵資值都能得到 當然還有8分 9分和12分 如果面值分...