并查集与二分图染色法
原理:把相同颜色的放进一个联通集合里面,建立一个数组,记录与根不相同的节点。
具体请看代码:
#include <bits/stdc++.h>
using namespace std;
#define FR freopen("in.txt","r",stdin)
#define FW freopen("out1.txt","w",stdout)
typedef long long ll;
struct pp
{
int from;
int to;
ll sad;
bool operator<(const pp & o)const
{
return sad > o.sad;
}
} g[100005];
struct UnionSet
{
int pre[20005];
UnionSet(int size)
{
for(int i = 0; i<size; i++)
{
pre[i] = i;
}
}
int find(int u)
{
return pre[u] == u ? u : pre[u] = find(pre[u]);
}
void unite(int u,int v)
{
pre[find(u)] = find(v);
}
bool isConnect(int u,int v)
{
return find(u) == find(v);
}
};
int h[20005];
int main()
{
int n,m;
cin >> n >> m;
for(int i = 0; i<m; i++)
{
cin >> g[i].from >> g[i].to >> g[i].sad;
}
sort(g,g+m);
UnionSet us(n+1);
ll ans = 0;
for(int i = 0; i<m; i++)
{
int ur = us.find(g[i].from);
int vr = us.find(g[i].to);
if(ur != vr) // 根节点不相同,说明处于不同颜色
{
if(h[ur]) us.unite(vr,h[ur]); // 如果有与ur互异的节点,那么他一定是和vr处于统一联通分量中
if(h[vr]) us.unite(ur,h[vr]); // 如果有与vr互异的节点,那么他一定是和ur处于统一联通分量中
h[ur] = vr; // ur互异的节点是vr
h[vr] = ur; // vr互异的节点是ur
}else // 根节点相同,无法染色构成二分图
{
ans = g[i].sad;
break;
}
}
cout << ans;
return 0;
}