#这题用并查集!!
刚一开始看的时候懵了,这题怎么做,后来看了一下别人的题解,别人也没怎么说明白,最后自己根据别人的代码手动模拟了一下。跟你们说下我的理解与感悟。
#include<iostream> #include<cstdio> #include<algorithm> #include<cstring> #define X 100000+7 using namespace std; int fa[X];//父亲 struct Node{ int u,v,w; }map[X];//罪犯之间的关系 bool pd(Node a,Node b) { return a.w>b.w; }//重新定义sort的排序,由大到小排序 int find(int x) { if(fa[x]==x)return x; return fa[x]=find(fa[x]); }//查找父亲节点 int hb(int x,int y) { int ff=find(x),fff=find(y); fa[ff]=fff; }//并查集的合并 int main() { int n,m; scanf("%d%d",&n,&m); for(int i=1;i<=2*n;++i)//这里是一个难点,有的同学就要问了,为什么i要在1和2*n之间定义呢,我们是把n+1~2*n定义为1~n罪犯的敌人(互相看不服的罪犯)为什么要用2*n呢,因为n是不确定的,要找到他的敌人,就要开2倍的数组
{ fa[i]=i; } for(int i=1;i<=m;++i) { scanf("%d%d%d",&map[i].u,&map[i].v,&map[i].w); } sort(map+1,map+m+1,pd);//这里由大到小排序,运用了贪心思想。因为要保证看到的最小,所以要保证俩个火气大的罪犯分开
for(int i=1;i<=m;++i) { int ff=find(map[i].u),fff=find(map[i].v); if(ff==fff)//如果俩互相看不服对方的罪犯在同一监狱,就输出他们之间的火气值,因为火气值是从大到小排序的,之后就算有互相看不服的罪犯在同一监狱,也比此时的火气值小
{ cout<<map[i].w; return 0; } hb(map[i].u,map[i].v+n);//这时要让互相看不服对方的X,Y。X要与Y之后看不服的罪犯合住一监狱 hb(map[i].v,map[i].u+n);//同上 } cout<<0;//若最后没有发生火气值,直接输出就好了 }