日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

UESTC_酱神寻宝 2015 UESTC Training for Dynamic ProgrammingProblem O

發布時間:2024/4/17 编程问答 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 UESTC_酱神寻宝 2015 UESTC Training for Dynamic ProgrammingProblem O 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

O - 醬神尋寶

Time Limit: 3000/1000MS (Java/Others) ??? Memory Limit: 65535/65535KB (Java/Others)
Submit?Status

醬神來到了一座小島,島上有n個箱子。

一共有3中不同的鑰匙,金鑰匙、銀鑰匙和萬能鑰匙。醬神一開始有a把金鑰匙、b把銀鑰匙和c把萬能鑰匙。

i個箱子上有xi把金鎖,yi把銀鎖。金鑰匙只能打開金鎖,銀鑰匙只能打開銀鎖,萬能鑰匙兩種鎖都能打開。用于打開鎖的鑰匙會立刻損壞,醬神會丟掉損壞的鑰匙。箱子里有ai把金鑰匙、bi把銀鑰匙和ci把萬能鑰匙,想要取出箱內的鑰匙必須要打開這xi+yi把鎖。

醬神的目的是使他擁有的鑰匙總數最多。一旦醬神認為自己已經擁有了最多的鑰匙,他就不會去開剩下的箱子了。

Input

第一行一個數n

接下來有n行。每行5個數,xi,yi,ai,bi,ci

最后一行3個數a,b,c

1=<n<=15

0=<xi,yi,ai,bi,ci,a,b,c<=10

Output

輸出一個數醬神的最多鑰匙數。

Sample input and output

Sample InputSample Output
3 1 0 0 0 1 2 4 0 8 0 3 9 10 9 8 3 1 2 8
1 0 0 1 2 3 0 0 0 6

Hint

第一個樣例中醬神會打開第一個和第二個箱子。

?

解題思路:

首先貪心,能用金 / 銀就不用萬能鑰匙.

我們不妨令 f ( i , j ) -> 開啟箱子的狀態為 i , 金鑰匙為 j 把時能獲得最多的萬能鑰匙.

之后我們考慮更新,設 0 為沒開啟過, 1 為開啟過.

每次更新都是由 x 個 0 的狀態更新到 x+1 個 0 的狀態.

我們采用bfs維護這種順序即可

?

不過由于本題數據很水,各位可以嘗試各種花式方法水過去!!

?

#include <iostream> #include <algorithm> #include <cstring> #include <cstdio> #include <queue> /*f( i , j ) - > 當前開的箱子的集合為 i , 金鑰匙的數目是 j 時可以獲得的最多萬能鑰匙數目. */using namespace std; const int maxn = 15; int n,sta,stb,stc,f[1 << 15][ maxn*11 ],ans = 0; typedef struct Item {int needA,needB,getA,getB,getC; };typedef struct updatastatus {int st,number; updatastatus(const int &st,const int &number){this->st = st , this->number = number;} };bool arrived[1 << 15][maxn * 11]; queue<updatastatus>q; Item A[maxn+3];inline void updata(int i,int j,int newans) {f[i][j] = max(f[i][j],newans); }//可以開啟為 0 , 不能開啟為 1; int main(int argc,char *argv[]) {scanf("%d",&n);for(int i = 0 ; i < n ; ++ i) scanf("%d%d%d%d%d",&A[i].needA,&A[i].needB,&A[i].getA,&A[i].getB,&A[i].getC);scanf("%d%d%d",&sta,&stb,&stc);f[0][sta] = stc; // Init;memset(arrived,false,sizeof(arrived));q.push(updatastatus(0,sta));while(!q.empty()){updatastatus ns = q.front();q.pop();int ra = ns.number, rb, rc = f[ns.st][ns.number] , all = sta + stb + stc , st = ns.st;for(int i = 0 ; i < n ; ++ i)if (ns.st >> i & 1)all += A[i].getA + A[i].getB + A[i].getC - A[i].needA - A[i].needB;ans = max(ans,all);rb = all - ra - rc;for(int i = 0 ; i < n ; ++ i){if (!(st >> i & 1)){int needA = A[i].needA;int needB = A[i].needB;int getA = A[i].getA;int getB = A[i].getB;int getC = A[i].getC;if (ra >= needA) //金夠 {if (rb >= needB) //金銀都夠 {updata(st | (1 << i) , ra - needA + getA, rc + getC);if (!arrived[st | (1 << i)][ra - needA + getA]){q.push(updatastatus(st | (1 << i),ra - needA + getA));arrived[st | (1 << i)][ra - needA + getA] = true;} }else //金夠銀不夠 {if (needB- rb <= rc){updata(st | (1 << i) , ra - needA + getA, rc - needB + rb + getC);if (!arrived[st | (1 << i)][ra - needA + getA]){q.push(updatastatus(st | (1 << i),ra - needA + getA));arrived[st | (1 << i)][ra - needA + getA] = true;} }}}else{if (rb >= needB) //金不夠銀夠 {if (needA - ra <= rc){updata(st | (1 << i) , getA, rc - needA + ra + getC);if (!arrived[st | (1 << i)][getA]){q.push(updatastatus(st | (1 << i),getA));arrived[st | (1 << i)][getA] = true;} }}else //金不夠銀不夠 {if (needA - ra + needB - rb <= rc){updata(st | (1 << i) , getA, rc - needA + ra - needB + rb + getC);if (!arrived[st | (1 << i)][getA]){q.push(updatastatus(st | (1 << i),getA));arrived[st | (1 << i)][getA] = true;} } } }}}}printf("%d\n",ans);return 0; }

?

轉載于:https://www.cnblogs.com/Xiper/p/4539658.html

總結

以上是生活随笔為你收集整理的UESTC_酱神寻宝 2015 UESTC Training for Dynamic ProgrammingProblem O的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。