题目链接:http://poj.org/problem;jsessionid=8C1721AF1C7E94E125535692CDB6216C?id=1417

题意:有p1个天使,p2个恶魔,天使只说真话,恶魔只说假话。问n句话,问x:y是否为天使,x回答yes或no,分别表示是或否,问能否确认为天使的人的编号(1..p1+p2),若能按顺序1输出,否则输出no。

思路:

看到带权并查集的题首先考虑到向量,先分析一下,不访设x->y表示x说y是什么,0表示天使,1表示是恶魔,枚举一下会发现x->y=0也表示x y同类,=1表示x y异类。并且x->z=(x->y)^(y->z)。这样就很清晰了,我们使用并查集将有关系的人并起来,并得到每个人与其祖先的关系,这样之后就会得到一些集合,每个集合有两类人。我想到这了就不知道怎么做了,因为我是在刷bin巨并查集专题看到的这题,我的潜意识就是怎么用并查集去解决这个问题,所以我一直在想是不是有其他的并查集的方法。看了别人的博客才恍然大悟之后就是一个完全背包的题了啊。还是太年轻了,思维应该开阔些,不能局限在一种思维上去想怎么做题。

回到题目,利用并查集得到这些集合比较简单,稍微熟悉并查集都能想到,接下来的背包DP和路径回溯才是这道题的核心。先遍历一遍用r[i]表示第i个集合的祖先,用a[i][0]表示第i个集合与祖先同类的人数,用a[i][1]表示第i个集合与祖先异类的人数。之后就是dp部分,dp[i][j]表示前i个集合中天使个数为j的方法数,按背包模板来就行。当dp[tot][p1]==1时有解,否则输出“no"。若有解还需要输出编号,只需要从dptot][p1]往前回溯即可,因为要按升序,需要sort一下。至此这道题才算结束,但因为敲错了一个变量名,我找了一个小时bug,写代码时还是要心细,不然太折磨人了。

代码如下:

 #include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std; int n,p1,p2,x,y,d;
int root[],f[],dp[][],r[],a[][],res[]; int getr(int k){
if(root[k]==k) return k;
else{
int tmp=root[k];
root[k]=getr(root[k]);
f[k]^=f[tmp];
return root[k];
}
} int main(){
while(scanf("%d%d%d",&n,&p1,&p2),n||p1||p2){
for(int i=;i<=p1+p2;++i)
root[i]=i,f[i]=,a[i][]=a[i][]=;
while(n--){
char ch[];
scanf("%d%d%s",&x,&y,ch);
if(ch[]=='y') d=;
else d=;
int rx=getr(x),ry=getr(y);
if(rx!=ry){
root[ry]=rx;
f[ry]=f[x]^f[y]^d;
}
}
int tot=;
memset(dp,,sizeof(dp));
for(int i=;i<=p1+p2;++i){
if(i==getr(i)){
r[++tot]=i;
for(int j=;j<=p1+p2;++j)
if(getr(j)==i)
if(f[j]==) a[tot][]++;
else a[tot][]++;
}
}
dp[][]=;
for(int i=;i<=tot;++i){
for(int j=p1;j>=a[i][];--j)
dp[i][j]+=dp[i-][j-a[i][]];
for(int j=p1;j>=a[i][];--j)
dp[i][j]+=dp[i-][j-a[i][]];
}
if(dp[tot][p1]!=){
printf("no\n");
continue;
}
int p=p1,num=;
for(int i=tot;i>=;--i)
if(dp[i-][p-a[i][]]==){
for(int j=;j<=p1+p2;++j)
if(getr(j)==r[i]&&f[j]==)
res[num++]=j;
p-=a[i][];
}
else{
for(int j=;j<=p1+p2;++j)
if(getr(j)==r[i]&&f[j]==)
res[num++]=j;
p-=a[i][];
}
sort(res,res+num);
for(int i=;i<num;++i)
printf("%d\n",res[i]);
printf("end\n");
}
return ;
}

poj1417(带权并查集+背包DP+路径回溯)的更多相关文章

  1. poj1417 带权并查集 + 背包 + 记录路径

    True Liars Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 2713   Accepted: 868 Descrip ...

  2. poj1417 带权并查集+0/1背包

    题意:有一个岛上住着一些神和魔,并且已知神和魔的数量,现在已知神总是说真话,魔总是说假话,有 n 个询问,问某个神或魔(身份未知),问题是问某个是神还是魔,根据他们的回答,问是否能够确定哪些是神哪些是 ...

  3. 西安邀请赛-D(带权并查集+背包)

    题目链接:https://nanti.jisuanke.com/t/39271 题意:给定n个物品,m组限制,每个物品有个伤害值,现在让两个人取完所有物品,要使得两个人取得物品伤害值之和最接近,输出伤 ...

  4. 洛谷P1196 [NOI2002]银河英雄传说(带权并查集)

    题目描述 公元五八○一年,地球居民迁至金牛座α第二行星,在那里发表银河联邦创立宣言,同年改元为宇宙历元年,并开始向银河系深处拓展. 宇宙历七九九年,银河系的两大军事集团在巴米利恩星域爆发战争.泰山压顶 ...

  5. 【11.1校内测试】【快速幂DP】【带权并查集】【模拟】

    Solution $jzy$大佬用了给的原根的信息,加上矩阵快速幂150行QAQ 然而$yuli$大佬的做法不仅好懂,代码只有50行! 快速幂的思想,把m看成要组成的区间总长度,每次将两段组合得到新的 ...

  6. [NOIP摸你赛]Hzwer的陨石(带权并查集)

    题目描述: 经过不懈的努力,Hzwer召唤了很多陨石.已知Hzwer的地图上共有n个区域,且一开始的时候第i个陨石掉在了第i个区域.有电力喷射背包的ndsf很自豪,他认为搬陨石很容易,所以他将一些区域 ...

  7. luogu 2294 狡猾的商人 带权并查集

    此题做法多啊 带权并查集,区间dp,前缀和,差分约束 1.自己写的前缀和, 11 #include<bits/stdc++.h> #define rep(i,x,y) for(regist ...

  8. POJ 1733 Parity game (带权并查集)

    题意:有序列A[1..N],其元素值为0或1.有M条信息,每条信息表示区间[L,R]中1的个数为偶数或奇数个,但是可能有错误的信息.求最多满足前多少条信息. 分析:区间统计的带权并查集,只是本题中路径 ...

  9. POJ1984:Navigation Nightmare(带权并查集)

    Navigation Nightmare Time Limit: 2000MS   Memory Limit: 30000K Total Submissions: 7871   Accepted: 2 ...

随机推荐

  1. ThinkJava-多态

    8.2.1 方法调用绑定 解决的办法就是后期绑定,它的含义就是在运行时根据对象的类型进行绑定.后期绑定也 叫做动态绑定或运行时绑定.如果一种语言想实现后期绑定,就必须具有某种机制,以便在运 行时能判断 ...

  2. [转][SVN]常用操作

    1.  Commit 提交当前代码到 SVN 服务器. 2. 引用第三方类库时,不要从安装位置引用,而是在解决方案下,添加一个 lib 的目录,把需要的程序集复制到这里,然后从 lib 目录引用. 3 ...

  3. 深入浅出 JIT 编译器

    转载 https://www.ibm.com/developerworks/cn/java/j-lo-just-in-time/ JIT 编译器在运行程序时有两种编译模式可以选择,并且其会在运行时决定 ...

  4. Distill详述「可微图像参数化」:神经网络可视化和风格迁移利器!

    近日,期刊平台 Distill 发布了谷歌研究人员的一篇文章,介绍一个适用于神经网络可视化和风格迁移的强大工具:可微图像参数化.这篇文章从多个方面介绍了该工具. 图像分类神经网络拥有卓越的图像生成能力 ...

  5. 关于raid5的一系列问题

    前几天我的一个同事在对计划采购的存储进行测试,期间聊到了raid5的话题,我和他的意见产生了分歧.他的说法是raid5不能挂太多盘是因为如果挂太多盘写惩罚会非常严重导致性能下降.而我的观点则是对于ra ...

  6. Kubernetes 无法删除pod实例的排查过程

    今天在k8s集群创建pod时,执行了如下命令: #kubectl run busybox-service --image=busybox --replicas=3 但是在创建过程中pod既然失败了, ...

  7. swagger配置

    1.pom.xml <!--swagger2--> <dependency> <groupId>io.springfox</groupId> <a ...

  8. 2017-2018-2 20165233 实验三 敏捷开发与XP实践

    20165233 实验三 敏捷开发与XP实践 实验内容 XP基础 XP核心实践 相关工具 实验步骤 一.编码标准 编程标准包含:具有说明性的名字.清晰的表达式.直截了当的控制流.可读的代码和注释,以及 ...

  9. 5. Java中序列化的serialVersionUID作用

    Java序列化是将一个对象编码成一个字节流,反序列化将字节流编码转换成一个对象. 序列化是Java中实现持久化存储的一种方法:为数据传输提供了线路级对象表示法. Java的序列化机制是通过在运行时判断 ...

  10. 8. mybatis实战教程(mybatis in action)之七:实现mybatis分页(源码下载)

    转自:https://blog.csdn.net/tangruyi1992/article/details/52584012 上 一篇文章里已经讲到了mybatis与spring MVC的集成,并且做 ...