HDU 4281 Judges' response 状态压缩 01背包 MTSP
来源:互联网 发布:如何解析json数据 编辑:程序博客网 时间:2024/06/01 10:10
题意:比赛上,有N个选手提出了问题,解决每个选手的问题需要的时间是Ci。现在每个裁判至多能为选手解答时间长为M的问题。至少需要几个裁判才能解决所有的选手的问题。
同时,给出每个选手的位置坐标xi,yi.希望所有裁判从起始点出发,解决完所有问题,再回到起始点,所走的距离和最小。
思路:其实这两问的答案是基本没有关系。唯一的关系,就是如果第一问没有解的话,第二问也是没有解的。所以,我们分别讨论这两个问题。
对于第一问,我们注意到,N很小,这是指数复杂度的一个标志。我们的目标是完成所有选手的问题,而这个可以利用状态压缩作为最终的目标。
因为我们要求至少需要多少个裁判,所以要先预处理一个裁判,可以完成那些选手的问题。
之后,就是状态压缩形式的01背包了。
对于第二问:如果问题简化为1个裁判的话,就是个旅行商问题,即用最短的距离访问所有的点并返回。要是裁判多了的话,其实就是个多旅行商问题(MTSP)。
对于MTSP问题,我们首先求出1个旅行商的TSP问题,这个可以用状态压缩的DP得到。
然后就是把单个旅行商合成多个旅行商,其实这也类似第一问的状态压缩形式的01背包。
注意:在TSP的问题中,要注意初始化,将起始的城市初始化为0.
代码如下:
#include <cstdio>#include <algorithm>#include <cstring>#include <bitset>#include <cmath>#include <vector>using namespace std;const int MAX = 17;int x[MAX],y[MAX],dis[MAX][MAX];int c[MAX],N,M;int dp[1<<MAX],dp2[1<<MAX][20],va[1<<MAX],vec[1<<MAX],sz,all;int judge(int s){ int sum = 0; for(int i = 0; i < N; ++i) if((s>>i) & 1) sum += c[i]; return va[s] = (sum <= M);}void pre_work(){ for(int i = 0; i < N; ++i){ for(int j = 0; j < i; ++j){ double dx = x[i] - x[j]; double dy = y[i] - y[j]; dis[i][j] = dis[j][i] = ceil(sqrt(dx*dx+dy*dy)); } dis[i][i] = 0; } sz = 0; all = (1<<N) - 1; for(int i = 0; i <= all; ++i) if(judge(i)) vec[sz++] = i;}int solve1(){ memset(dp,0x3f,sizeof(dp)); dp[0] = 0; for(int i = 0; i < sz; ++i){ for(int j = all; j >= 0; --j){ int s = j + vec[i]; if(s != (j | vec[i])) continue; dp[s] = min(dp[s],dp[j]+1); } } return dp[all];}int solve2(){ memset(dp2,0x3f,sizeof(dp2)); memset(dp,0x3f,sizeof(dp)); dp2[1][0] = 0; for(int s = 0; s <= all; ++s) if(va[s]) for(int i = 0; i < N; ++i) if((s>>i)&1){ dp[s] = min(dp[s],dp2[s][i] + dis[i][0]); for(int j = 0; j < N; ++j) if(!((s>>j)&1)) dp2[s|(1<<j)][j] = min(dp2[s|(1<<j)][j],dp2[s][i]+dis[i][j]); } for(int s = 0; s <= all; ++s) if(s&1) for(int j = (s-1) & s;j; j = (j-1) & s) dp[s] = min(dp[s],dp[j|1] + dp[(s-j) | 1]); return dp[all];}int main(void){ //freopen("input.txt","r",stdin); while(scanf("%d%d",&N,&M) != EOF){ for(int i = 0; i < N; ++i) scanf("%d%d",&x[i],&y[i]); for(int i = 0; i < N; ++i) scanf("%d",&c[i]); pre_work(); int ans1 = solve1(); if(ans1 == 0x3f3f3f3f) puts("-1 -1"); else printf("%d %d\n",ans1,solve2()); } return 0;}
0 0
- HDU 4281 Judges' response 状态压缩 01背包 MTSP
- hdu4281 Judges' response(状态压缩+mtsp+01背包)
- hdu - 4281 - Judges' response - dp / 01背包 / mTSP
- HDU - 4281 Judges' response(MTSP)
- HDU 4182 Judges' response(01背包+TSP状态压缩DP)
- HDU 4281 (状态压缩+背包+MTSP)
- HDU 4281 Judges' response(12年天津 MTSP问题)
- HDU4281 Judges' response(状态压缩+01背包+分组背包)经典
- **HDU 4281 - Judges' response(DP`背包+TSP)
- HDU4281:Judges' response(mTSP问题)
- hdu 4281 judges' response
- HDU 4281 Judges' response
- HDU 4281 Judges' response dp+tsp极致
- HDU 4281 Judges' response(状压DP)
- hdu 4281 Judges' response(多旅行商&DP)
- hdu 4281(MTSP)
- hdu4281 状态压缩~MTSP最优值
- hdu 4281 Judges' response 状压DP+TSP ★★★★
- Oracle数据库,实例,表空间,用户,表之间的关系简析
- Python安装Scrapy爬虫工具
- Cocos2d-X 3.4版-地图无限滚动与边缘检测《赵云要格斗》
- java 中的 '\0'
- block
- HDU 4281 Judges' response 状态压缩 01背包 MTSP
- 笛卡儿积的Java算法实现
- Codeforces Round #290 (Div. 1)B. Fox And Jumping
- linux 进程调度策略
- javascript对url进行encode的两种方式
- POJ 3294 (UVA 11107) Life Forms 后缀数组
- Java线程面试题 Top 50
- hdu 2846 Repository 字典树的一种变形
- Func和Action,委托与lambda表达式,一看就知道