题目:
10 51 10 1007 10 281 3 324 6 416 6 1 Sample Output1 Source2009 Multi-University Training Contest 13 - Host by HIT Recommendgaojie | We have carefully selected several similar problems for you: 3033 3035 3036 3037 3031 思路:题意:有 n 个数,你不知道它们的值, 然后又有 m 行数,每行 a ,b ,c,表示 a 到 b 之间所有数的和为c(包含了第a个和第b个数)。但是这m行数里面有些是错的,就是与前面给的条件相冲突的,要求你最后输出错了几行。用r录每一个点跟根节点的关系。首先我们可以把问题稍微转化一下,就是如果已知[3,6],[7,10]俩个区间内各自所有数的和,那么就可以[3,10]内所有数的和,可是,这俩个区间根本就不衔接,所有要稍微处理一下,将左区间值减1,就变成了[2,6],[6,10],这样就方便处理了。既然这样的话,[2,6]区间内所有数的和就完全可以等价于点2到点7之间的距离了。代码:
#include <cstdio>#include <cstring>#include <cstdlib>#include <cmath>#include <string>#include <iostream>#include <stack>#include <queue>#include <vector>#include <algorithm>#define mem(a,b) memset(a,b,sizeof(a))#define N 1000+20#define M 200010#define MOD 1000000000+7#define inf 0x3f3f3f3fusing namespace std;int n,m;int f[M],r[M];void init()//初始化并查集{ for(int i=0; i<=n; i++) { f[i]=i; r[i]=0; }}int find(int x){ if(x==f[x]) return f[x]; int t=find(f[x]); r[x]+=r[f[x]];//r[x]表示x到f[x]的距离,r[f[x]]表示的是父节点与根节点之间的距离 f[x]=t; return f[x];}int func(int x,int y){ if(x>y) return x-y; else return y-x;}int mix(int x,int y,int sum){ int fx=find(x); int fy=find(y); if(fx==fy) { if(func(r[x],r[y])==sum) return 0; else return 1;//有错误了就返回1 } else { f[fx]=fy; r[fx]=sum+(r[y]-r[x]); return 0; }}int main(){ while(~scanf("%d%d",&n,&m)) { int a,b,v,ans=0; init(); for(int i=1; i<=m; i++) { scanf("%d%d%d",&a,&b,&v); a--;//左值-1方便处理 if(mix(a,b,v)) ans++; } printf("%d/n",ans); } return 0;}
新闻热点
疑难解答