动物王国中有三类动物A,B,C,这三类动物的食物链构成了有趣的环形。A吃B, B吃C,C吃A。
现有N个动物,以1-N编号。每个动物都是A,B,C中的一种,但是我们并不知道它到底是哪一种。

有人用两种说法对这N个动物所构成的食物链关系进行描述:

第一种说法是"1 X Y",表示X和Y是同类。

第二种说法是"2 X Y",表示X吃Y。

此人对N个动物,用上述两种说法,一句接一句地说出K句话,这K句话有的是真的,有的是假的。当一句话满足下列三条之一时,这句话就是假话,否则就是真话。

1) 当前的话与前面的某些真的话冲突,就是假话;

2) 当前的话中X或Y比N大,就是假话;

3) 当前的话表示X吃X,就是假话。

你的任务是根据给定的N(1 <= N <= 50,000)和K句话(0 <= K <= 100,000),输出假话的总数。

Input

第一行是两个整数N和K,以一个空格分隔。

以下K行每行是三个正整数 D,X,Y,两数之间用一个空格隔开,其中D表示说法的种类。

若D=1,则表示X和Y是同类。

若D=2,则表示X吃Y。

Output

只有一个整数,表示假话的数目。

Sample Input

100 7
1 101 1
2 1 2
2 2 3
2 3 3
1 1 3
2 3 1
1 5 5

Sample Output

3

每两个动物间三种关系:同类,吃和被吃。然后判断断言d x y假话的个数。

并查集的归类fa[]指当前确定的关系,具体是什么关系用别的数组用值表示,比如带权值的,同类或者互吃(?)关系的。。

用fa[a],re[a]分别存和a有关的集合中的代表元素序号,和x与其关系。为了程序简便,一种给三种关系分别标识的方案为:同类 0,x吃fa[a]为1,x被fa[a]吃为-1。然后在find()中需要更新re[a]为相对find(fa[a])的关系时,找规律简化写作:

if(re[a]==re[fa[a]]) re[a] = -re[a];
else re[a] = re[a]+re[fa[a]];

解释:如果re[a]==re[fa[a]],就是a与fa[a]、fa[a]与find(fa[a])的关系一样,即吃,同类,被吃。因为三种之间关系是a吃b b吃c c吃a,则a吃fa[a]吃find(fa[a]),那么a被find(fa[a])吃。同类的话,因为-0=0,所以对应的上。else中类似,写一下能发现符合规律。。还有一种方案是同类0 吃2 被吃1,然后见:https://blog.csdn.net/libing923/article/details/8240995/

嗯,这个也挺像函数的,还有点像离散数学里的关系的合成,所以来一个函数,compose(rea, reb),其中b=fa[a],rea=re[a],reb=re[b],返回rea,reb两个关系的合成结果。

新断言d x y时,先根据题目描述x y不能大于n,然后如果x==y 判断d是否为1,不是就ans++。过了这两个判断条件后判断x y是不是已经在一个集合(就是能否根据已知确定x y关系)在的话判断是否符合,不在就把这个新关系加入进去:

 if (x>n || y>n)
ans++;
else if (x==y) {
ans+=(d==);
}
else {
rx = finf(x); ry = finf(y);//找xy的代表findfather,并更新其与代表的关系
if (rx == ry) { //如果同一个代表,可以确定关系:
ans+=(re[x] != compose((d-), re[y]));//注1
}
else { //新关系加入
fa[ry]=rx;
re[ry] = compose(compose(-re[y], -(d-)), re[x]);//注2
}
}

注1:判断x与y的关系是否与d一样。d-1后恰好表示x对y的关系(d-1==0,xy同类;==1,x吃y),而re[x]表示x对rx/ry的关系,re[y]表示y对rx/ry的关系,所以合成d-1和re[y]应得到x对rx的关系,也就是相等,所以可以这么写

注2:-re[y]表示ry对y的关系(多了个负号),各种值与y对re[y]相反。其余 同理,rx ry x y ,有三层关系,ry->y->x->rx,最后得到re[ry]对其新爸爸的关系了。嗯,也可以写fa[rx]=ry,就是让ry当rx和ry之前各自所代表的一直关系的集合中所有元素合并后的新爸爸。然后更新re[rx]也是一样的。

哎,写之前习惯性的加了个while(EOF!=scanf())结果WA,彷徨之中去了竟然就AC了。。就AC了。。嗦不粗话

还有初始化的时候要初始化re[i],因为这个都是相对代表的值,代表必须是“清白的”。。

总:

 #include <cstdio>
#include <cstring> #define ll long long
#define MAXN 50005 #define SIM 0
#define EAT 1
#define EAN -1 int fa[MAXN], re[MAXN]; int n, k;
int d, x, y;
int rx, ry;
int ans=; int compose(int a, int b) {
if (a==b)return -a;
else return a+b;
} int finf(int a) {
if (fa[a] == a) return a; int root = finf(fa[a]);
re[a] = compose(re[a], re[fa[a]]);
return fa[a] = root;
} int main()
{
scanf("%d%d", &n, &k);
for (int i = ; i <= n; i++) fa[i] = i, re[i] = ;
ans = ;
for(int i = ; i < k; i++) {
scanf("%d%d%d", &d, &x, &y);
if (x>n || y>n)
ans++;
else if (x==y) {
ans+=(d==);
}
else {
rx = finf(x); ry = finf(y);
if (rx == ry) {
ans+=(re[x] != compose((d-), re[y]));
}
else {
fa[ry]=rx;
re[ry] = compose(compose(-re[y], -(d-)), re[x]);
}
}
}
printf("%d\n", ans); return ;
}

B-食物链-经典并查集的更多相关文章

  1. POJ 1182 食物链 经典并查集+关系向量简单介绍

    题目: 动物王国中有三类动物A,B,C,这三类动物的食物链构成了有趣的环形.A吃B, B吃C,C吃A. 现有N个动物,以1-N编号.每个动物都是A,B,C中的一种,但是我们并不知道它到底是哪一种. 有 ...

  2. HDU1232 畅通工程---(经典并查集应用)

    http://acm.hdu.edu.cn/showproblem.php?pid=1232 畅通工程 Time Limit: 4000/2000 MS (Java/Others)    Memory ...

  3. POJ 1182 食物链(经典并查集) (多组输入有时乱加也会错!)

      多组输入有时乱加也会错! 这次用多组输入竟然,不用竟然对了,所以以后做题目,若是答案错误,先看加上或者删掉多组输入,看对不对 食物链 Time Limit: 1000MS   Memory Lim ...

  4. POJ1182食物链(并查集经典好题)

    题目链接:http://acm.hust.edu.cn/vjudge/contest/view.action?cid=66964#problem/E 题目思路:主要有两种思路:1.带权并查集2.挑战程 ...

  5. 关押罪犯 and 食物链(并查集)

    题目描述 S 城现有两座监狱,一共关押着N 名罪犯,编号分别为1~N.他们之间的关系自然也极不和谐.很多罪犯之间甚至积怨已久,如果客观条件具备则随时可能爆发冲突.我们用"怨气值"( ...

  6. NOI2001|POJ1182食物链[种类并查集 向量]

    食物链 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 65430   Accepted: 19283 Description ...

  7. HDU 5652 India and China Origins(经典并查集)

    特别经典的一个题,还有一种方法就是二分+bfs 题意:空间内n*m个点,每个点是0或者1,0代表此点可以走,1代表不能走.接着经过q年,每年一个坐标表示此点不能走.问哪年开始图上不能出现最上边不能到达 ...

  8. POJ1182 食物链(并查集)

    食物链 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 55260   Accepted: 16210 Description ...

  9. POJ 1182 :食物链(并查集)

    食物链 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 43526   Accepted: 12679 Description ...

  10. POJ1182--食物链(经典并查集)并查集看不出来系列2

    食物链 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 65906   Accepted: 19437 Description ...

随机推荐

  1. C#流程控制语句--分支语句(if,switch,三位运算符)

    分支语句:判断结构要求程序员指定一个或多个要评估或测试的条件,以及条件为真时要执行的语句(必需的)和条件为假时要执行的语句(可选的). 分支语句  if if(判断条件表达式) {//表达式结果为tu ...

  2. ECharts前端图形展示

    这次负责慢查询预警,前后端都是自己处理,这次遇到了前端作图的需求,做一个记录以便后续使用: 使用的作图方式是ECharts,相应的example官方有相应的文档和使用方法,比较简单,一下只贴链接: h ...

  3. 一个axios的简单教程

    转载于:https://www.jianshu.com/p/13cf01cdb81f 转载仅供个人学习 首先要明白的是axios是什么:axios是基于promise(诺言)用于浏览器和node.js ...

  4. promise用法十道题

    JS是单线程语言,多数的网站不需要大量计算,程序耗时主要是在磁盘I/O和网络I/O上 ,虽然固态硬盘SSD读取很快,但是和CPU比起来却不在一个数量级上,而且网络上的一个数据包来回时间更慢,所以一些C ...

  5. python线程condition条件锁应用实例

    import time import threading # 吃火锅鱼丸 guo = [] suo = threading.Condition() #条件锁 # 生产者负责生产 class Produ ...

  6. PHP的json_encode()函数与JSON对象

    一.问题描述 这周搬砖的时候,前端通过ajax获取后端的数据后,照例用 对象.属性 的方式取值,然而结果总是总是不能如预期般展示在页面上. 先写个 demo 还原下场景:选中一个下拉框列表选项后,会在 ...

  7. weka安装&配置&使用

    安装与配置: 官网下载安装即可,分为带jre和不带jre版本,3.8需要jre1.8.如果装了1.7的话,还是自己先装一个1.8再装不带jre版本的比较好,不然weka装的会让人一脸懵逼,不知道装在哪 ...

  8. day25_python_1124

    1.内容回顾 2.作业讲解 3.今日作业 4.粘包问题 5.tcp和udp 6.udp-socket 7.udp-socket 多人聊天 8.socketserver-tcp-socket并发 9.p ...

  9. SQL Server数据库开发的二十一条军规

    如果你正在负责一个基于SQL Server的项目,或者你刚刚接触SQL Server,你都有可能要面临一些数据库性能的问题,这篇文章会为你提供一些有用的指导(其中大多数也可以用于其它的DBMS).在这 ...

  10. centos7搭建时间服务器

    时区概念 GMT.UTC.CST.DST UTC:整个地球分为二十四个时区,每个时区都有自己的本地时间,在国际无线电通信场合,为了统一起见,使用一个统一的时间,称为通用协调时间(UTC:Univers ...