类似区间计数的种类并查集两题--HDU 3038 & POJ 1733
1.POJ 1733
| Time Limit: 1000MS | Memory Limit: 65536K | |
| Total Submissions: 5744 | Accepted: 2233 |
Description
You suspect some of your friend's answers may not be correct and you want to convict him of falsehood. Thus you have decided to write a program to help you in this matter. The program will receive a series of your questions together with the answers you have received from your friend. The aim of this program is to find the first answer which is provably wrong, i.e. that there exists a sequence satisfying answers to all the previous questions, but no such sequence satisfies this answer.
Input
Output
Sample Input
10
5
1 2 even
3 4 odd
5 6 even
1 6 even
7 10 odd
Sample Output
3
1.题目数据量较大,要用map来做哈希。
2.num[x]表示(fa[x],x]区间1的个数的奇偶性,0代表偶数,1代表奇数。以树根作为参照,每个点的num值即为树根到该点之间1的个数的奇偶性。
输入a,b
首先判断a,b是否在同一集合,如果在,则以其共同树根作为参照点,看异或值是否为0或1(0代表偶数,1代表奇数)。
如果不在,则合并两个集合,画一个图就知道了,图类似:http://www.cnblogs.com/whatbeg/p/3503585.html 中的图类似,假设fa[x] = y;
则 num[x] = num[a] ^ num[b] ^ k; (k = 0/1)
代码:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <map>
using namespace std;
#define N 10100 int fa[N],num[N];
map<int,int> mp; void makeset(int n)
{
for(int i=;i<=;i++)
{
fa[i] = i;
num[i] = ;
}
} int findset(int x)
{
if(x != fa[x])
{
int tmp = fa[x];
fa[x] = findset(fa[x]);
num[x] = num[x]^num[tmp];
}
return fa[x];
} int unionset(int a,int b,char oe)
{
int x = findset(a);
int y = findset(b);
int k = (oe == 'o'? :);
if(x == y)
{
if(num[a]^num[b] == k)
return ;
else
return ;
}
else
{
fa[x] = y;
num[x] = num[a]^num[b]^k;
return ;
}
} int main()
{
int n,m,i,k,a,b,cnt;
char ss[];
scanf("%d%d",&n,&m);
makeset(n);
k = ;
cnt = ;
for(i=;i<=m;i++)
{
scanf("%d%d %s",&a,&b,ss);
a = a-;
if(mp.find(a) == mp.end())
{
mp[a] = k++;
}
if(mp.find(b) == mp.end())
{
mp[b] = k++;
}
if(unionset(mp[a],mp[b],ss[]))
cnt++;
else
break;
}
printf("%d\n",cnt);
return ;
}
2.HDU 3038
题目大意:有n次询问,给出a到b区间的总和,问这n次给出的总和中有几次是和前面已近给出的是矛盾的,即命题为假的次数。
分析:与上面那题一样,用根节点作参照,每个点维护一个sum值,表示到根节点的距离,树根的距离为0。如果我们知道a到b之间的关系,a到c之间的关系,那么我们就可以知道a,b,c任意两个之间的关系。
输入a,b,判断是否属于同一集合,如果是,则判断 sum[b] - sum[a] 是否等于val。
如果不在同一集合,则合并,此时又画一个四点图可知, fa[y] = x; sum[y] = sum[b] - sum[a] + k; 不懂的话自己可以画一下。
然后就好搞了。
代码
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
using namespace std;
#define N 200100 int fa[N],sum[N]; void makeset(int n)
{
for(int i=;i<=n;i++)
{
fa[i] = i;
sum[i] = ;
}
} int findset(int x)
{
if(x != fa[x])
{
int tmp = fa[x];
fa[x] = findset(fa[x]);
sum[x] = sum[x] + sum[tmp];
}
return fa[x];
} int unionset(int a,int b,int k)
{
int x = findset(a);
int y = findset(b);
if(x == y)
{
if(sum[b] - sum[a] == k)
return ;
else
return ;
}
else
{
fa[y] = x;
sum[y] = sum[a] - sum[b] + k;
return ;
}
} int main()
{
int n,m,i,a,b,cnt,val;
while(scanf("%d%d",&n,&m)!=EOF)
{
makeset(n);
cnt = ;
for(i=;i<=m;i++)
{
scanf("%d%d%d",&a,&b,&val);
a = a-;
if(unionset(a,b,val))
cnt++;
}
printf("%d\n",cnt);
}
return ;
}
类似区间计数的种类并查集两题--HDU 3038 & POJ 1733的更多相关文章
- poj1733(区间上的种类并查集)
题目大意是:一个由0,1组成的数字串~~,现在你问一个人,第i位到第j位的1的个数为奇数还是偶数.一共会告诉你几组这样的数 要你判断前k组这个人回答的都是正确的,到第k+1组,这个人说的是错的,要你输 ...
- poj1182(种类并查集好题)
不得不说,我得感谢@驱动幽灵百鬼夜行小肆,正是因为看明白了他给出的解析,我才完全弄懂种类并查集的,这里,我也不想去改其他的,就直接引用他的解题报告吧 转载:http://blog.csdn.net/c ...
- (并查集 建立关系)Parity game -- POJ -1733
链接: http://poj.org/problem?id=1733 http://acm.hust.edu.cn/vjudge/contest/view.action?cid=82830#probl ...
- 【转】并查集&MST题集
转自:http://blog.csdn.net/shahdza/article/details/7779230 [HDU]1213 How Many Tables 基础并查集★1272 小希的迷宫 基 ...
- HDU3038【种类并查集】
题意: 给出m组区间[a,b],以及其区间的和,问有矛盾的有几组: 思路: 种类并查集. 主要是几个关系:同类元素的关系,父亲与儿子的关系,不同类元素的关系: 我们可以类似看作一个前缀和,sum[x] ...
- NOI2001|POJ1182食物链[种类并查集 向量]
食物链 Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 65430 Accepted: 19283 Description ...
- hdu 3038 How Many Answers Are Wrong(种类并查集)2009 Multi-University Training Contest 13
了解了种类并查集,同时还知道了一个小技巧,这道题就比较容易了. 其实这是我碰到的第一道种类并查集,实在不会,只好看着别人的代码写.最后半懂不懂的写完了.然后又和别人的代码进行比较,还是不懂,但还是交了 ...
- HDU - 3038 种类并查集
思路:种类并查集的每个节点应该保存它的父节点以及他和父节点之间的关系.假设root表示根结点,sum[i-1]表示i到根结点的和,那么sum[j-1] - sum[i]可以得到区间[j, i]的和.那 ...
- 种类并查集(洛谷P2024食物链)
题目描述 动物王国中有三类动物 A,B,C,这三类动物的食物链构成了有趣的环形.A 吃 B,B 吃 C,C 吃 A. 现有 N 个动物,以 1 - N 编号.每个动物都是 A,B,C 中的一种,但是我 ...
随机推荐
- 四、MyBatis主配置文件
//备注:该博客引自:http://limingnihao.iteye.com/blog/1060764 在定义sqlSessionFactory时需要指定MyBatis主配置文件: Xml代码 收藏 ...
- SDK Build Tools revision (19.0.3) is too low for project Min
SDK Build Tools revision (19.0.3) is too low for project Min(转) 如果你正在使用Android Studio工具进行开发,且将 ...
- 备份一张iPhone拍照写入exif中的orientation图片
- PHP控制前台弹出对话框
应用场景: 微信授权登录过程中,需要用户确认,故衍生此需求: 相应的逻辑不放在前端的原因是,此部分逻辑属于偏功能业务,所以放在后端,方便统一管理. 解决办法: 通过php echo出javascrip ...
- parseInt第二个参数详解
前阵子在stackOverflow上看到两个这样的问题: 为什么parseInt(8,3) == NaN,parseInt(16,3) == 1? 为什么parseInt('dsff66',16) = ...
- [ html canvas 透明度 globalApha ] canvas绘图属性 透明度 globalApha 属性演示
<!DOCTYPE html> <html lang='zh-cn'> <head> <title>Insert you title</title ...
- Android获取焦点所在控件
View vFocus=getWindow().getDecorView().findFocus(); if(vFocus instanceof EditText) { ((EditText) vFo ...
- 【Android开发资料分享】自己整理的Android开发资料,非常全面
学习Android以来,不知不觉中收集了大量非常优秀的Android开发资料,一直没有系统的整理,最近抽时间把收藏夹中的资料做了一下整理,现在分享给大家,希望能够帮助到需要的人.这份资料我还会不断的更 ...
- [android] 手机卫士界面切换动画
在/res/anim/ 建立文件tran_out.xml 添加<translate>节点 设置x轴来源坐标android:fromXDelta=”0” 设置x轴目的坐标android:to ...
- iOS开发笔记12:iOS7上UITextField限制字数输入导致崩溃问题
在一些场景中,需要限制用户的输入字数,例如在textField里进行控制(textView也类似,崩溃原因也相同),如图所示 系统会监听文本输入,需要注意的第一点是输入法处于联想输入还未确定提交的时候 ...