看清题啊大哥。。。人家说存在k个,正好包含k种。你看成了刚好k个,刚好k种,然后在那用什么set搞来搞去,还出了bug然后刚好过了样例,神逗。
先验证解法的正确性,再去编写代码,别浪呀,万一没想清楚甚至读错题就爆炸啦。
好吧,其实中文题目还是有点没说清楚的吧。以后还是看英文原题好了。
英文原题就是说如果将N个不同的化合物放在一起恰好有N种元素,就会爆炸,还用成环解释了一波。这不就懂了嘛= =。
判断成环的方法我只知道,dfs,拓扑排序,还有个什么Bellman-Ford,还有个什么Floyd判圈算法。其中拓扑排序只适用于有向图,Bellman-Ford太低效以及大材小用了,Floyd判圈算法速度很慢,但缺点是不需要建图,一般用于更抽象的数学问题而不是用于解决图论上的问题。其实突然想起来大半年前做过一道题,在某些时候,并查集可以一战。因为并查集可以判断连通,所以某些时候也可以判断环的,但缺点是无向。比如最小生成树里面不就用来判断新加入的边是否成环了么。他可以判断一条新加入的边是否连在同一个连通块上。所以说某种程度上也算是判断环的方法。然后其实这道题本质上不就是生成树么= =。
代码
#include<bits/stdc++.h>
#define maxn 100010
using namespace std;
int fa[maxn];
void init()
{
for(int i=0;i<maxn;i++) fa[i]=i;
}
int f(int x)
{
return x==fa[x]?x:fa[x]=f(fa[x]);
}
int main()
{
while(1)
{
init();
int x,y;
int cnt=0;
while(1)
{
if(scanf("%d",&x)==EOF) return 0;
if(x==-1)
{
printf("%d\n",cnt);
break;
}
scanf("%d",&y);
int a=f(x);
int b=f(y);
if(a==b) cnt++;
else fa[a]=b;
}
}
return 0;
}