题目链接:http://poj.org/problem?id=1015

大概题意:

  法庭要挑选m人陪审团。先随机挑选n个公民,对于每个公民,控辩双方都有各自的“喜好度”p[ ] 和 d[ ],法庭要尽量保证陪审团的m人中控方总喜好度和辩方总喜好度的差值的绝对值尽可能小,如果最佳的结果有多个,那么就选择控辩双方总喜好度最高的那个。

解题思路:

  日常不会dp题,哭),。。。思路源于网络

  设一个二维数组 dp[i][j], i代表“使用”了几个人,j代表控辩双方喜好度之差,为了避免出现数组下标为负的情况,我们可以把j值的最后再加上20*m。

  状态转移方程:dp[ i+1 ][ j+dat[i+1] ] = min(dp[i+1][ j+dat[i+1] ] , dp[i][j]+sum[i+1] )。sum[i+1] =  p[i+1] + d[i+1], dat[i+1] = p[i+1] - d[i+1] 。

  用vector记录路径,操作方便的出奇。

  Waring: 要把选取哪个人这个循环放在最外层,不然会出现这种bug: 比如说 dp[5][y] = {1,2,3,5,6} = {1,2,3,7,8}, sum[5] + sum[6] = sum[7] + sum[8],  此时程序就有可能选择前面那个{1,2,3,5,6}这五个人,但是sum[5] 很大(大于剩下的所有sum),到了 dp[6][x]的时候,由于第5人已经被选取了,所以他无法再选择第五人,但是如果当初选择的是sum[7]+sum[8],此时就可以选择sum[5]了,很明显,后者会更优,所以程序会出bug。

AC代码:

 #include <cstdio>
#include <cstring>
#include <algorithm>
#include <vector>
using namespace std; const int inf=0x7ffffff;
int dp[][];
pair<int,int> pd[];
vector<int> path[][];
int main()
{
// freopen("in.txt","r",stdin);
// freopen("out.txt","w",stdout);
int n,m,a,b,cases=,min_n;
while(scanf("%d%d",&n,&m)==&&n&&m){
for(int i=;i<=n;i++)
scanf("%d%d",&pd[i].first,&pd[i].second);
min_n=*m;
for(int i=;i<=m;i++){
for(int j=;j<=*m;j++){
path[i][j].clear();
dp[i][j]=-inf;
}
}
dp[][min_n]=;
for(int k=;k<=n;k++){
int dat=pd[k].first-pd[k].second, sum=pd[k].first+pd[k].second;
for(int i=m-;i>=;i--){
for(int j=;j<=*m;j++){
if(dp[i][j]>=){
if(dp[i+][j+dat]<=dp[i][j]+sum){
dp[i+][j+dat]=dp[i][j]+sum;
path[i+][j+dat]=path[i][j];
path[i+][j+dat].push_back(k);
}
}
}
}
}
a=b=;
for(int i=;i<=*m;i++){
if(dp[m][min_n+i]>=||dp[m][min_n-i]>=){
int temp;
if(dp[m][min_n+i]>dp[m][min_n-i]) temp=min_n+i;
else temp=min_n-i;
for(int l=;l<m;l++){
int ind=path[m][temp][l];
a+=pd[ind].first,b+=pd[ind].second;
}
printf("Jury #%d\n",cases++);
printf("Best jury has value %d for prosecution and value %d for defence:\n",a,b);
for(int l=;l<m;l++) printf(" %d",path[m][temp][l]);
printf("\n\n");
break;
}
} }
return ;
}

POJ1015的更多相关文章

  1. [POJ1015]Jury Compromise

    题目大意:要求你从n个人中选出m个,每个人有两个值p[i],D[i],要求选出的人p总和与D总和的差值最小.若有相同解,则输出p总+D总最大的方案. 动态规划. 一直在想到底是n枚举外面还是m放外面, ...

  2. 【poj1015】 Jury Compromise

    http://poj.org/problem?id=1015 (题目链接) 题意 随机挑选n个人作为陪审团的候选人,然后再从这n个人中选m 人组成陪审团.选m人的办法是:控方和辩方会根据对候选人的喜欢 ...

  3. POJ1015 动态规划

    POJ1015 问题重述: 在n个候选者中选取m个人进入陪审团.每个候选者获得两项评分:D[j],P[j].求解最佳评审团,使得在每个成员的两项评分和之差 最小的情况下,使得两项评分和之和 最大. 分 ...

  4. POJ-1015(背包变形+输出路径)

    Jury Compromise POJ-1015 推荐几个较好的介绍和理解:https://blog.csdn.net/lyy289065406/article/details/6671105 htt ...

  5. NOI题库1980 陪审团的人选(POJ1015)

    1980:陪审团的人选 总时间限制: 1000ms 内存限制: 65536kB 描述 在遥远的国家佛罗布尼亚,嫌犯是否有罪,须由陪审团决定.陪审团是由法官从公众中挑选的.先随机挑选n个人作为陪审团的候 ...

  6. POJ1015 && UVA - 323 ~Jury Compromise(dp路径)

    In Frobnia, a far-away country, the verdicts in court trials are determined by a jury consisting of ...

  7. 【POJ1015】Jury compromise 多个费用的背包

    这是一道比较综合的动态规划问题. 首先,根据题目中的从N个人中选出M个人,并且要使得某个目标函数最优,可以想到是背包问题,且因为要取出M个人,人数也应该作为背包体积的一个维度. 其次,要求输出路径,因 ...

  8. poj1015 01二维背包

    /* 给定辩控双方给每个人的打分p[i],d[i], dp[j][k]表示前i个人有j个被选定,选定的人的辩控双方打分差之和是k,此状态下的最大辩控双方和 按01背包做,体积一维是1,体积二维是辩控双 ...

  9. poj-1015(状态转移的方向(01背包)和结果的输出)

    #include <iostream> #include <algorithm> #include <cstring> #include <vector> ...

  10. POJ1015陪审团(Jury Compromise)——dp+路径记录

    题目:http://poj.org/problem?id=1015 差值是有后效性的,所以“转化为可行性”,开一维记录“能否达到这个差值”. 当然可以开两维分别记录 a 和 b,但 “值只是0或1” ...

随机推荐

  1. js 实现动画功能,完整解析插件版 可更改配置参数[animate.js]

    前言:         本人纯小白一个,有很多地方理解的没有各位大牛那么透彻,如有错误,请各位大牛指出斧正!小弟感激不尽.         本篇文章为您分析一下原生JS写一个运动插件 基本功能: 补充 ...

  2. Android MVP 十分钟入门!

    前言 在日常开发APP 的过程中,随着业务的扩展,规模的变化.我们的代码规模也会逐渐变得庞大,每一个类里的代码也会逐渐增多.尤其是Activity和Fragment ,由于Context 的存在,基本 ...

  3. 使用Node.js的http-serve搭建本地服务器

    为什么要使用它? 首先,类似于vue-cli创建的项目,都能够实现浏览器中自动刷新,实时查看项目效果.其中的原理在于,webpack这样的工具启动了一个本地服务器,将本机当作一台服务器,这样在浏览器中 ...

  4. Geomesa-Hbase集群部署

    本文记录一下Geomesa-Hbase集群部署,在单机部署的基础上 https://www.cnblogs.com/help-silence/p/12817447.html 1.搭建集群 https: ...

  5. prufer编码学习笔记

    prufer 编码 对于一个无根树,他的 prufer 编码是这样确定的: 每次找到编号最小的一个叶子节点,也就是度数为\(1\)的节点,把和它相连的点,加入 prufer 编码序列的末尾,然后把这个 ...

  6. Codeforces 1332 D. Walk on Matrix(构造矩阵)

    怎么构造呢? \(首先我们不可能去构造一个2000*2000的矩阵,那太复杂了\) \(也许我们可以看看2*2的矩阵??\) \[\left[ \begin{matrix} x&y\\ z&a ...

  7. SpringBoot:整合Shiro

    目录 1.Shiro简介 1.1.什么是Shiro? 1.2.有哪些功能 1.3.Shiro架构(外部) 1.4.Shiro架构(内部) 2.HelloWorld 3.Shiro整合Spring Bo ...

  8. JavaScript 浅析数组对象与类数组对象

    数组(Array对象) 数组的操作 创建数组方法 添加与修改数组元素 删除数组元素 使用数组元素 遍历数组元素 多维数组 数组相关的函数 concat() join() pop() push() sh ...

  9. 一篇文章解决MongoDB的所有问题

    目录 一.MongoDB相关概念 1.1 业务应用场景 1.1.1 而MongoDB可应对"三高"需求· 1.1.2 什么时候选择MongoDB? 1.1.3 如果用mysql? ...

  10. NEON中的L可以避免溢出

    在做加法时,比如两个255x255的数值相加,那么正确结果将是130050,对一个最大值为65565的unsigned short是会溢出的,但是如果使用L命令时,则不会产生溢出.这说明L命令,不是先 ...