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

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

*【HDU - 5711】Ingress(tsp旅行商问题,优先队列贪心,状压dp,floyd最短路,图论)

發(fā)布時(shí)間:2023/12/10 编程问答 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 *【HDU - 5711】Ingress(tsp旅行商问题,优先队列贪心,状压dp,floyd最短路,图论) 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

題干:

Brickgao, who profited from your accurate calculating last year, made a great deal of money by moving bricks. Now he became ``gay shy fool'' again and recently he bought an iphone and was deeply addicted into a cellphone game called Ingress. Now he is faced with a problem so he turns to you for help again. We make some slight modifications based on the original rules, so please draw attention to the details below.?

There are?NN?portals (indexed from 1 to?NN) around Brickgao's home, and he can get some substances called XM by hacking the portals. It's known that for each portal?ii, he can get?AiAi?XM during the first hack, and after each hack, the amount of XM he will get during the next hack will decrease by?BiBi. If the amount of XM he can get is less than or equal to zero, Brickgao can't get XM from that portal anymore. For the?ii-th portal, if?Ai=10,Bi=2Ai=10,Bi=2?and he hacks 3 times, he will get 10, 8, 6 XM during each hack.?

There are?MM?bidirectional roads between some pairs of portals and between Brickgao's home and some portals. Now he is eager to start his Ingress journey from home and finally return home, but due to the extremely hot weather, Brickgao will feel sick when you hack more than?KK?times or the distance he covers is more than?LL. So how much XM he can get at most during this journey??
?

Input

The first line contains a single integer?T(T≤20)T(T≤20), indicating the number of test cases.?

The first line of each case are four integers?N(1≤N≤16),M(0≤M≤N(N+1)2),K(1≤K≤50)N(1≤N≤16),M(0≤M≤N(N+1)2),K(1≤K≤50)?and?L(2≤L≤2000)L(2≤L≤2000).?
The second line of each case contains?NN?non-negative integers where the?ii-th denotes?Ai(Ai≤500)Ai(Ai≤500).?
The third line of each case contains?NN?non-negative integers where the?ii-th denotes?Bi(Bi≤50)Bi(Bi≤50).?
Each of next?MM?line contains 3 non-negative integers?u,v(0≤u,v≤n)u,v(0≤u,v≤n)?and?c(0≤c≤1000)c(0≤c≤1000)?, denotes that there is a road with the length of?cc?between the?uu-th and the?vv-th portal. If?uu?or?vv?equals to 0, it means Brickgao's home.?

Output

For each test case, output the case number first, then the amount of maximum XM Brickgao can get.?

Sample Input

2 1 1 3 2 5 3 0 1 1 3 6 3 5 10 7 5 2 3 1 0 1 3 0 2 1 0 3 1 1 2 2 2 3 3 1 3 4

Sample Output

Case 1: 7 Case 2: 16

題目大意:

n(<=16)個(gè)點(diǎn)(其實(shí)還有個(gè)0點(diǎn)為home),m(<=n^2)條雙向邊和邊權(quán)(代表兩點(diǎn)之間距離<=1000),K(<=50)次hack機(jī)會(huì),最遠(yuǎn)走L(<=2000)路程

每個(gè)點(diǎn)的初始點(diǎn)權(quán)為a[i](<=500),每個(gè)點(diǎn)每hack一次點(diǎn)權(quán)下降b[i](<=50)(變?yōu)樨?fù)則當(dāng)然就不選啦)

對(duì)于每個(gè)點(diǎn),可以只經(jīng)過不hack,也可以到這個(gè)點(diǎn)之后一次性hack多次。

一個(gè)人從home出發(fā),最多hackK次,問在路程不超過L的情況下,可以獲得的最大價(jià)值。

解題報(bào)告:

因?yàn)榭梢灾唤?jīng)過不hack,所以先floyd跑一邊最短路(套路了),然后不難發(fā)現(xiàn)可以認(rèn)為:走過一個(gè)點(diǎn)之后不會(huì)再走回來,或者說,選擇了這個(gè)點(diǎn)hack了,就不會(huì)回來再hack這個(gè)點(diǎn)(因?yàn)檫€要多走距離,何必呢)(emmm其實(shí)上面說走過一個(gè)點(diǎn)之后不會(huì)再走回來不太合適,因?yàn)楫吘挂驗(yàn)樽疃搪?#xff0c;所以可能還是要回來的(因?yàn)檫@一點(diǎn)是最短路需要經(jīng)過的點(diǎn)嘛))這樣我們只需要記錄狀態(tài):走過了哪些點(diǎn),當(dāng)前在哪個(gè)點(diǎn)上,就可以跑(2^n * n)的dp了。
dp[sta][i]表示目前經(jīng)過點(diǎn)的狀態(tài)集合為i,當(dāng)前所在點(diǎn)的位置為 i 的最小路徑(當(dāng)然要加上返程到0點(diǎn)的路徑)
這是典型的旅行商問題。
由此得出所有可以到達(dá)的合法點(diǎn)集,其狀態(tài)用2進(jìn)制表示為sta。

對(duì)于每一個(gè)狀態(tài)sta,只要dp[sta][i]有一個(gè)i符合<=L,那么稱sta是合法狀態(tài)。
然后依次枚舉所有的合法sta,
對(duì)于每一個(gè)合法sta的所有點(diǎn)權(quán),用貪心原則,用優(yōu)先隊(duì)列選取最大的權(quán)值。

AC代碼:

#include<cstdio> #include<iostream> #include<algorithm> #include<queue> #include<map> #include<vector> #include<set> #include<string> #include<cmath> #include<cstring> #define F first #define S second #define ll long long #define pb push_back #define pm make_pair using namespace std; typedef pair<int,int> PII; const int MAX = 22; int dis[MAX][MAX],dp[1<<17][17]; int a[MAX],b[MAX]; int n,m,k,L; int up; bool ok[1<<17]; void floyd() {for(int k = 0; k<=n; k++) {for(int i = 0; i<=n; i++) {for(int j = 0; j<=n; j++) {dis[i][j] = min(dis[i][j],dis[i][k] + dis[k][j]);}}} } int tsp() {int ans = 0;for(int sta = 0; sta < up; sta++) ok[sta] = 0;memset(dp,0x3f,sizeof dp);dp[1][0]=0;for(int sta = 0; sta < up; sta++) {for(int i = 0; i<=n; i++) {if(dp[sta][i] <= L) {if(dp[sta][i] + dis[i][0] <= L) ok[sta] = 1;for(int j = 1; j<=n; j++) {dp[sta|(1<<j)][j] = min(dp[sta|1<<j][j], dp[sta][i] + dis[i][j]);}}}if(ok[sta]) {priority_queue<PII> pq;for(int i = 1; i<=n; i++) {if((sta&(1<<i) )!= 0) pq.push(pm(a[i],b[i]));}int tmp = 0;for(int i = 1; i<=k; i++) {if(pq.empty()) break;PII cur = pq.top();pq.pop();tmp += cur.F;cur.F -= cur.S;if(cur.F > 0) pq.push(pm(cur.F,cur.S)); }ans = max(ans,tmp);}}return ans; }int main() {int t,iCase=0;cin>>t;while(t--) {scanf("%d%d%d%d",&n,&m,&k,&L);up = (1<<(n+1));memset(dis,0x3f,sizeof dis);for(int i = 0; i<=n; i++) dis[i][i]=0;for(int i = 1; i<=n; i++) scanf("%d",a+i);for(int i = 1; i<=n; i++) scanf("%d",b+i);for(int q,w,e,i = 1; i<=m; i++) {scanf("%d%d%d",&q,&w,&e);if(e < dis[q][w]) dis[q][w]=dis[w][q]=e;}floyd();printf("Case %d: %d\n",++iCase,tsp());} return 0 ; }

貼另一個(gè)做法:https://blog.csdn.net/qq_37025443/article/details/83513413

總結(jié)

以上是生活随笔為你收集整理的*【HDU - 5711】Ingress(tsp旅行商问题,优先队列贪心,状压dp,floyd最短路,图论)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。