并查集——奇偶性(Parity)
2024-10-08 05:06:09
题目描述
•有一个01序列,长度<=1000000000,现在有n条信息,每条信息的形式是-a
b even/odd。表示第a位到第b位元素之间的元素总和是偶数/奇数。
b even/odd。表示第a位到第b位元素之间的元素总和是偶数/奇数。
•你的任务是对于这些给定的信息,输出第一个不正确的信息所在位置-1。信息的数目不超过5000。
•如果信息全部正确,即可以找到一个满足要求的01序列,那么输出n。
输入
•输入文件
•第一行一个整数m表示01序列的长度,第二行一个整数n表示信息的数目。
•接下来是n条信息
输出
输出第一条错误信息的位置-1.
如果没有错误信息,则输出n
样例输入
10
5
1 2 even
3 4 odd
5 6 even
1 6 even
7 10 odd
样例输出
3
这道题可以用并查集的思路做
将第三行数据的1 2看做半开半闭区间( 0 , 2 ]中的所有整数元素,他们的和是偶数,可将0当做2的父亲,他们之间的距离为0(偶数mod2的余数)
以此类推,如果为奇数,则他们之间的距离为1
那么,输入x和y,找到他们各自的父亲g和h,如果g不等于h,则无需验证,将g作为h的父亲,其距离计算公式为:
s[ h ]=( s[ x ] + m - s[ y ] )%2
其中m为x到y的和的奇偶性(看不懂就慢慢想)
如果,g等于h,则进行验证,看看abs( s[ x ] - s[ y ] )%2是否满足此语句的奇偶性
整体思路到位
接下来,由于输入的x和y最大为十亿,无法开出这么大的数组,则必须将其理想化
由于只有5000条语句,所以元素最多只有10000个,则用数组将输入的x和y装进去,要验证的时候直接数组里面找,将其在数组中的编号代替其本身进行运算
还不明白?看代码吧:
- #include<cstdio>
- #include<cstring>
- #include<cmath>
- #include<algorithm>
- using namespace std;
- int abs(int x){return x>=0?x:-x;}
- int a[10001];
- int f[10001],s[10001];
- int m,n,k;
- int find(int x)//找父亲与离父亲的距离,顺便找沿路所有元素与离父亲的距离(看不懂?自己慢慢想)
- {
- if(f[x]==0)return x;
- int xx=find(f[x]);
- s[x]+=s[f[x]];
- s[x]%=2;
- return f[x]=xx;
- }
- int main()
- {
- int i,j;
- scanf("%d%d",&m,&n);
- for(i=1;i<=n;i++)
- {
- char c[11];
- int x,y,r1,r2;
- scanf("%d%d%s",&x,&y,c);
- if(x>m||y>m){printf("%d",i-1);return 0;}
- if(x>y)swap(x,y);
- x--;//半开半闭区间,小的元素减减
- bool p=0,q=0;
- for(j=1;j<=k;j++)//找数组中是否有x和y
- <span style="white-space:pre"> </span>{
- if(a[j]==x&&!p)x=j,p=1;
- if(a[j]==y&&!q)y=j,q=1;
- }
- if(!p)a[++k]=x,x=k;//没有就将其加进去
- if(!q)
- {
- if(x!=y)a[++k]=y,y=k;//这里要注意
- else y=x;
- }
- r1=find(x),r2=find(y);
- if(r1!=r2)
- {
- if(r1>r2)swap(r1,r2);
- f[r2]=r1;
- if(c[0]=='o')s[r2]=abs(s[x]+1-s[y])%2;
- else s[r2]=abs(s[x]-s[y])%2;
- }
- else//验证
- {
- if(c[0]=='o'&&abs(s[x]-s[y])%2!=1){printf("%d",i-1);return 0;}
- if(c[0]=='e'&&abs(s[x]-s[y])%2){printf("%d",i-1);return 0;}
- }
- }
- printf("%d",n);
- }
最新文章
- XP之后Windows的一些变化
- [FMX] Android APP 启动黑屏优化补丁
- 《C#编程》课件 - C#基础
- .Net中几种常见的页面跳转传值方法
- 数字转换为壹仟贰佰叁拾肆的Java方法
- UVA5870 乱搞 Smooth Visualization
- R语言缺失值信息处理
- Mahout之Canopy Clustering深入理解
- [C# 基础知识系列]专题四:事件揭秘
- 绘图quartz之阴影
- uva 755 - 487--3279
- 【转】android TV CTS 4.0.3_r1测试
- Glide的加载图片的帮助类,用来把图片圆角或者改成圆形图片
- elasticsearch-5.0.0初见
- Galaxy (hdu 5073 数学)
- Unity 的几种打包姿势(android)
- 剑指Offer——笔试题+知识点总结
- (八)喜马拉雅Demo引出的细节(代理模式和图片缩放)
- 【SpringCloud】Zuul在何种情况下使用Hystrix
- vm Linux centos 链接外网
热门文章
- 【u034】追查坏奶牛
- 推荐:mysql锁 innodb下的记录锁,间隙锁,next-key锁
- Node.js入门-知识整理
- C#获取美团评价信息
- CentOS7.6部署k8s环境
- PyCharm永久破解方法
- 「洛谷P2397」 yyy loves Maths VI (mode) 解题报告
- kubelet--help-v1.15.4
- PHP 对接第三方 LINE 登录,网上找到相关的不多 但是网上哪些乱七八糟的啰啰嗦嗦 要么就是怎么做的, 什么步骤 总会给你省略, 如果有幸你看到我的 可以放心的复制即用, 当然 你也可以用postman去尝试 不过我觉得既然做开发 就没必要那个了! 如果用postman再最后一步的时候 请用本文最下方式
- netcore 自动生成Dockerfile的坑