国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > C++ > 正文

Round D APAC Test 2017 Problem D. Stretch Rope (C++)

2019-11-08 02:19:57
字體:
供稿:網(wǎng)友

PRoblem

Mary likes playing with rubber bands. It’s her birthday today, and you have gone to the rubber band shop to buy her a gift.

There are N rubber bands available in the shop. The i-th of these bands can be stretched to have any length in the range [Ai, Bi], inclusive. Two rubber bands of range [a, b] and [c, d] can be connected to form one rubber band that can have any length in the range [a+c, b+d]. These new rubber bands can themselves be connected to other rubber bands, and so on.

You want to give Mary a rubber band that can be stretched to a length of exactly L. This can be either a single rubber band or a combination of rubber bands. You have M dollars available. What is the smallest amount you can spend? If it is impossible to accomplish your goal, output IMPOSSIBLE instead.

Limits

1 ≤ T ≤ 100. 1 ≤ Pi ≤ M. 1 ≤ L ≤ 10000. 1 ≤ Ai ≤ Bi ≤ 10000. Small dataset

1 ≤ N ≤ 10. 1 ≤ M ≤ 100. Large dataset

1 ≤ N ≤ 1000. 1 ≤ M ≤ 1000000000.

分析:

小數(shù)據(jù)應(yīng)該可以通過暴力解決,對所有的N個rubber bands,枚舉出所有2^N種子集,并判斷每種組合是否滿足長度要求,并選取其中最小花費(fèi)即可。但對于大數(shù)據(jù)來說 2^N太大了。選用動態(tài)規(guī)劃來解決, 這邊也參考了scoreboard上前幾位作者的代碼。

動態(tài)規(guī)劃:

設(shè)數(shù)組dp[L+1],其中dp[i]表示要達(dá)到長度為i的rubber band所需最少花費(fèi)。對每個rubber band按順序考慮到數(shù)組dp中去,即首先考慮只有前1個band時dp的狀態(tài),再考慮只有前2個band時dp的狀態(tài),……,最后考慮前N個band時的dp狀態(tài),考察dp[L]是否小于預(yù)算M即可。初始時將所以dp元素設(shè)為MAX, dp[0]=0當(dāng)考慮第i個rubber band進(jìn)入dp數(shù)組時,因?yàn)槠淅扉L度可以達(dá)到[Ai,Bi], 所以對dp[j]來說,只需取dp數(shù)組中下標(biāo)為j-Bi到j(luò)-Ai這一段中最小值+Pi 來決定是否更新當(dāng)前dp[j]。(注意j-Bi到j(luò)-Ai不要越界)當(dāng)?shù)趇個rubber band進(jìn)入考慮范圍時,按上述更新一遍dp數(shù)組即可。

但是, 對每個j查找“dp數(shù)組中下標(biāo)為j-Bi到j(luò)-Ai這一段中最小值”很耗時,考慮到其實(shí)是一個滑動窗口中的最小值,可借鑒leetcode239減少復(fù)雜度。 但一開始用deque實(shí)現(xiàn)比較耗時,后來直接用數(shù)組實(shí)現(xiàn)就變快了。

代碼:Github

#include <iostream>#include <math.h>#include <vector>#include <algorithm>#include <deque>using namespace std;typedef long long ll;int T;int main() { FILE *fin, *fout; fin=fopen("D-large-practice.in", "r"); fout = fopen("output", "w"); fscanf(fin, "%d", &T); for (int kk = 1; kk <= T; kk++) { int num, money, length; fscanf(fin, "%d %d %d", &num, &money, &length); vector<ll> dp(length + 1, INT_MAX); dp[0] = 0; for (ll i = 0; i < num; i++) { int a, b; int p; fscanf(fin, "%d %d %d", &a, &b, &p); //尋找長度為b-a+1的sliding window中最小值的下標(biāo) 記錄到que中 vector<int> que(length + 1, 0); int start = 0; int end = 0; for (int k = a; k < b&&length - k >= 0; k++) { while (end > start && dp[que[end - 1]] >= dp[length - k]) end--; que[end++] = length - k; } for (ll j = length; j >= 0; j--) { if (j - b >= 0) { while (end > start && dp[que[end - 1]] >= dp[j - b]) end--; que[end++] = j - b; } if (start < end) dp[j] = min(dp[j], dp[que[start]] + p); if (dp[start] >= j - a) start++; } } if (dp[length] <= money) fprintf(fout, "Case #%d: %d/n", kk, dp[length]); else fprintf(fout, "Case #%d: IMPOSSIBLE/n", kk); } }
發(fā)表評論 共有條評論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表

圖片精選

主站蜘蛛池模板: 亚东县| 泰兴市| 儋州市| 石屏县| 贞丰县| 化德县| 丹寨县| 公主岭市| 聂拉木县| 五原县| 吴江市| 洞头县| 玉田县| 咸宁市| 遂平县| 云霄县| 团风县| 苗栗市| 岳池县| 南皮县| 龙里县| 扎鲁特旗| 吴江市| 南乐县| 平顶山市| 页游| 当涂县| 绥化市| 浦县| 石泉县| 淳化县| 永福县| 潼南县| 宝丰县| 枣庄市| 华容县| 腾冲县| 余庆县| 福海县| 鄂托克旗| 家居|