In Frobnia, a far-away country, the verdicts in court trials are determined by a jury consisting of members of the general public. Every time a trial is set to begin, a jury has to be selected, which is done as follows. First, several people are drawn randomly from the public. For each person in this pool, defence and prosecution assign a grade from 0 to 20 indicating their preference for this person. 0 means total dislike, 20 on the other hand means that this person is considered ideally suited for the jury. 
Based on the grades of the two parties, the judge selects the jury. In order to ensure a fair trial, the tendencies of the jury to favour either defence or prosecution should be as balanced as possible. The jury therefore has to be chosen in a way that is satisfactory to both parties. 
We will now make this more precise: given a pool of n potential jurors and two values di (the defence's value) and pi (the prosecution's value) for each potential juror i, you are to select a jury of m persons. If J is a subset of {1,..., n} with m elements, then D(J ) = sum(dk) k belong to J 
and P(J) = sum(pk) k belong to J are the total values of this jury for defence and prosecution. 
For an optimal jury J , the value |D(J) - P(J)| must be minimal. If there are several jurys with minimal |D(J) - P(J)|, one which maximizes D(J) + P(J) should be selected since the jury should be as ideal as possible for both parties. 
You are to write a program that implements this jury selection process and chooses an optimal jury given a set of candidates.

Input

The input file contains several jury selection rounds. Each round starts with a line containing two integers n and m. n is the number of candidates and m the number of jury members. 
These values will satisfy 1<=n<=200, 1<=m<=20 and of course m<=n. The following n lines contain the two integers pi and di for i = 1,...,n. A blank line separates each round from the next. 
The file ends with a round that has n = m = 0.

Output

For each round output a line containing the number of the jury selection round ('Jury #1', 'Jury #2', etc.). 
On the next line print the values D(J ) and P (J ) of your jury as shown below and on another line print the numbers of the m chosen candidates in ascending order. Output a blank before each individual candidate number. 
Output an empty line after each test case.

Sample Input

4 2
1 2
2 3
4 1
6 2
0 0

Sample Output

Jury #1
Best jury has value 6 for prosecution and value 4 for defence:
2 3

Hint

If your solution is based on an inefficient algorithm, it may not execute in the allotted time.
题意:

在一个遥远的国家弗罗地亚,法庭审判的裁决由一个由普通大众组成的陪审团决定。

每次审判开始时,都必须选择一个陪审团,具体做法如下。首先,有几个人是从公众中随机抽取的。

对于这个池中的每个人来说,辩护和起诉分配从0到20的等级,表示他们偏爱这个人。

0意味着完全不喜欢,20另一方面意味着这个人被认为是理想的陪审团。
根据双方的等级,法官选择陪审团。为了确保公平的审判,陪审团支持辩护或起诉的趋势应尽可能平衡。

因此,陪审团必须以双方满意的方式选择。
我们现在要做的更加精确:给予每个潜在陪审员我有n个潜在陪审员和两个价值di(辩护人的价值)和pi(检察官的价值),

你应该选择一个m人陪审团。如果J是具有m个元素的{1,...,n}的子集,则D(J)= sum(dk)k属于J
并且P(J)= sum(pk)k属于J是这个辩护和起诉陪审团的总值。
对于最佳陪审团J,值| D(J) - P(J)|必须最小化。如果存在几个最小| D(J) - P(J)|的陪审团,

应该选择最大化D(J)+ P(J)的陪审团,因为陪审团对于双方来说应尽可能理想。
你应该编写一个程序来实现这个陪审团的选择过程,并为一组候选人选择一个最佳陪审团。

上一篇博客我写的是,最长上升子序列的变形,求DP路径

这篇是01背包的变形也需要求路径,现在我会的DP也就背包和最长上升子序列。

求| D(J) - P(J)|的最小值

我现在对DP的感觉就是求最优解。也许这就是菜鸡吧。

这题的转移方程我还没有推出来,还是靠看大佬博客才会的。

先讲DP等下再去讲路径,

dp[i][j]表示选择了 i 个人  差值和 | D(J) - P(J)|  = j  ,在这个两个条件下的和值 D(J)+ P(J)的最大值。

构造了一个二维DP 就很好的可以推出转移方程了。

应该这个差值有正有负 所以我就设参考点为 pmax=20*m,这个是初始点,

这样处理的原因是怕数组越界。毕竟没有下标为负数的元素。

最后的一个问题就是打印路径了

这里用的是vector 数组进行处理 因为这题的数据比较少,用vector也行,

这题还有一个坑点就是,可能会出现重复选择的情况

所以for (int k=0 ;k<n ;k++ )  这样就可以避免了数据重复了,

最后一点DP的初始化还是难啊

 #include<cstdio>
#include<ctype.h>
#include<algorithm>
#include<iostream>
#include<cstring>
#include<vector>
using namespace std;
int n,m,cas=,dp[][],a[],b[];
vector<int>path[][];
int main() {
while(scanf("%d%d",&n,&m),n,m){
for (int i= ;i< ;i++) {
for (int j= ;j< ;j++) {
dp[i][j]=-;
path[i][j].clear();
}
}
for (int i= ;i<n ;i++) {
int x,y;
scanf("%d%d",&x,&y);
a[i]=x-y;
b[i]=x+y;
}
int pmax=*m;
dp[][pmax]=;
for (int k= ;k<n ;k++ ){
for (int i=m- ;i>= ;i--){
for (int j= ;j<*pmax ;j++){
if (dp[i][j]>= ) {
if (dp[i+][j+a[k]]<=dp[i][j]+b[k]){
dp[i+][j+a[k]]=dp[i][j]+b[k];
path[i+][j+a[k]]=path[i][j];
path[i+][j+a[k]].push_back(k);
}
}
}
}
}
int i;
for (i= ; dp[m][pmax+i]==- && dp[m][pmax-i]==- ;i++);
int temp=(dp[m][pmax+i]>dp[m][pmax-i]) ? i:-i;
int sump=(dp[m][pmax+temp]+temp)/;
int sums=(dp[m][pmax+temp]-temp)/;
printf("Jury #%d\n",cas++);
printf("Best jury has value %d for prosecution and value %d for defence: \n",sump,sums);
for (int i= ;i<m ;i++) {
printf(" %d",path[m][pmax+temp][i]+);
}
}
return ;
}

POJ1015 && UVA - 323 ~Jury Compromise(dp路径)的更多相关文章

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

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

  2. POJ-1015 Jury Compromise(dp|01背包)

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

  3. $POJ1015\ Jury\ Compromise\ Dp$/背包

    洛谷传送门 $Sol$ 这是一道具有多个“体积维度”的$0/1$背包问题. 把$N$个候选人看做$N$个物品,那么每个物品有如下三种体积: 1.“人数”,每个候选人的“人数”都是$1$,最终要填满容积 ...

  4. POJ 1015 Jury Compromise dp分组

    第一次做dp分组的问题,百度的~~ http://poj.org/problem?id=1015 题目大意:在遥远的国家佛罗布尼亚,嫌犯是否有罪,须由陪审团决定.陪审团是由法官从公众中挑选的.先随机挑 ...

  5. POJ 1015 Jury Compromise dp

    大致题意: 从n个候选人中选出m个人作为陪审团.为了让陪审团的选择更公平,辩方和控方都为这n个候选人给出了满意度(辩方为D[j],控方为P[j],范围0至20).现在要使得选出的m位候选人的辩方总和与 ...

  6. POJ 1015 Jury Compromise(双塔dp)

    Jury Compromise Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 33737   Accepted: 9109 ...

  7. poj1015 Jury Compromise【背包】

    Jury Compromise Time Limit: 1000MS   Memory Limit: 65536K Total Submissions:32355   Accepted:8722   ...

  8. 【题解】Jury Compromise(链表+DP)

    [题解]Jury Compromise(链表+DP) 传送门 题目大意 给你\(n\le 200\)个元素,一个元素有两个特征值,\(c_i\)和\(d_i\),\(c,d \in [0,20]\), ...

  9. 背包系列练习及总结(hud 2602 && hdu 2844 Coins && hdu 2159 && poj 1170 Shopping Offers && hdu 3092 Least common multiple && poj 1015 Jury Compromise)

    作为一个oier,以及大学acm党背包是必不可少的一部分.好久没做背包类动规了.久违地练习下-.- dd__engi的背包九讲:http://love-oriented.com/pack/ 鸣谢htt ...

随机推荐

  1. VLOOKUP函数常用套路大全

    今天和大家来说说VLOOKUP的那些事儿,深入了解一下VLOOKUP函数的各种用法,看看这位大众情人还藏着多少不为人知的秘密.函数的语法为:VLOOKUP(要找谁,在哪儿找,返回第几列的内容,精确找还 ...

  2. 部署wcf出现的问题与解决方法

    我将本机作为服务器开发时,没出什么问题,将wcf服务端寄缩到另一台电脑上时,出现了一些问题,这里总结下: 1.wcf服务器和另一个网站应用出问题 服务器的iis上有一个网站应用,当我将wcf服务寄缩到 ...

  3. json字符串对象内嵌json对象

    有时候需要在json的key:value字符串对象中再嵌入一个json对象,如果需要把如下的json对象作为字符串嵌入到json字符串对象中: { "type": 2, " ...

  4. Dubbo学习1-Hello world

    前言 互联网技术到今天已经非常成熟和稳定了,其中为了解决高并发.大规模的服务请求,出现了微服务.RPC这样的分布式架构.今天就从头开始学习RPC框架dubbo. 为什么要学Dubbo 关于分布式的解决 ...

  5. vuex2中使用mapMutations/mapActions报错解决方法 BabelLoaderError: SyntaxError: Unexpected token

    在尝鲜vuex2时,发现vuex2增加了 mapGetters 和 mapActions 的方法,借助stage2的 Object Rest Operator 特性,可以写出下面代码:methods: ...

  6. 理解python的元类

    看了一篇文档,借鉴一下!写下自己对python元类的理解,欢迎各位大神给出意见. 我的理解就是 type用来创建元类,元类用来创建类,类用来创建实例 这样一想,是不是可以认为元类创建类的过程等同于类创 ...

  7. 打造Linux回收站

    linux是没有回收站概念的,一旦误删除文件了是很难很难找回来的,对普通用户而言误删除文件就等于永久性不可逆丢失数据了:不过可以改造一下rm命令来变相实现回收站功能,实际上就是mv命令转移文件到指定路 ...

  8. Algorithm --> 树中求顶点A和B共同祖先

    树中求顶点A和B共同祖先 题目: 给定一颗树,以及两个顶点A和B,求最近的共同祖先,和包含的子顶点个数? 比如:给定如下图的树,以及顶点13和8,则共同祖先为3,以3为root的子顶点共有8个

  9. java开源安全框架-------Apache Shiro--第二天

    身份验证 即在应用中谁能证明他就是他本人.一般提供如他们的身份ID一些标志信息来表明他就是他本人,如提供身份证.用户名.密码来证明 在shiro中,用户需要提供principals(身份)和crede ...

  10. 转载--MYSQL5.7:Access denied for user 'root'@'localhost' (using password:YES)解决方法

    1.打开MySQL目录下的my.ini文件,在文件的最后添加一行"skip-grant-tables",保存并关闭文件; 2.重启MySQL服务; 3.通过cmd行进入MySQL的 ...