【NOIP 校内模拟】T1 line(带权并查集)

很无奈 离正解就差一句话

简单的带权并查集 没啥好说的 也可以差分约束

#include<bits/stdc++.h>
#define N 100005
#define M 200005
#define D 10005
using namespace std;
template<class T>
inline void read(T &x)
{
	x=0; int f=1;
	static char ch=getchar();
	while((!isdigit(ch))&&ch!='-')	ch=getchar();
	if(ch=='-')	f=-1,ch=getchar();
	while(isdigit(ch))	x=x*10+ch-'0',ch=getchar();
	x*=f;
}
int n,m;
int father[N],to_root[N];
inline int getfather(int x)
{
	if(father[x]==x)	return x;
	int fa=father[x];
	father[x]=getfather(father[x]);
	to_root[x]+=to_root[fa];
	return father[x];
}
int minx[N],maxx[N];
int main()
{
	read(n),read(m);
	for(register int i=1;i<=n;i++)	father[i]=i;
	for(register int i=1;i<=m;i++)
	{
		int x,y,z;
		read(x),read(y),read(z);
		if(z<0)	swap(x,y),z=-z;
		int fx=getfather(x); int fy=getfather(y);
		if(fx==fy)
		{
			if(to_root[x]+z!=to_root[y])
			{
				puts("impossible");
				return 0;
			}
		}
		else
		{
			father[fy]=fx;
			to_root[fy]=to_root[x]+z-to_root[y];
		}
	}
	int ans=0;
	for(int i=1;i<=n;i++)
	{
		int fa=getfather(i);
		minx[fa]=min(minx[fa],to_root[i]);
		maxx[fa]=max(maxx[fa],to_root[i]);
	}
	for(int i=1;i<=n;i++)	ans=max(ans,maxx[i]-minx[i]);
	cout<<ans;
	return 0;
}
posted @ 2018-11-05 13:58  Patrickpwq  阅读(115)  评论(0编辑  收藏  举报