题意:m个区间,及其和。问有几个错误。
思路:sigma[l~r]=sigma[r]-sigma[l-1]。如果l-1和r有相同的最left值,说明它们的差值在之前已经准确的算出来了,只要判断是否和给的sum相同即可。否则之前没准确算出来,就可以把它们合并。合并注意回溯代码顺序问题,一定要返回par[x]
#include <stdio.h>
#include <iostream>
using namespace std;
const int MAXN=200000+5;
int v[MAXN];
int par[MAXN];
int Find(int x)
{
int temp=par[x]; //保存原父亲的编号
if(par[x]!=x)
{
par[x]=Find(par[x]);
v[x]+=v[temp]; // 秩最多为3,这是关键。每次Find都会进行路径压缩,然后直接连接到根节点上。
}
return par[x]; //return 可以保证秩从3变到2
}
int main(void)
{
int n,m;
while((scanf("%d%d",&n,&m))!=EOF)
{
for(int i=0; i<=n; i++)
par[i]=i,v[i]=0;
int ans=0;
for(int i=1; i<=m; i++)
{
int l,r,sum;
scanf("%d%d%d",&l,&r,&sum);
l--;
int rootl=Find(l),rootr=Find(r);
if(rootl==rootr)
{
if(v[r]-v[l]!=sum) ans++;
}
else if(rootl<rootr) //向量关系,手动画图
{
par[rootr]=rootl;
v[rootr]=sum+v[l]-v[r];
}
else if(rootl>rootr)
{
par[rootl]=rootr;
v[rootl]=-(sum+v[l])+v[r];
}
}
cout << ans << endl;
}
return 0;
}