Tarjan+Kruskal求助
查看原帖
Tarjan+Kruskal求助
1121518
StarsIntoSea楼主2024/6/9 23:59

WA 10 pts 就 a 了1、2

刚学重构树甚至没看参考代码就直接写了,实在调不出来了

//重构树中点权和边权做了区分
#include <stdio.h>
#include <vector>
#include <algorithm>
using namespace std;
#define N 100002
#define M 500002
#define MAXM 2000002
struct node{
	int u,v,w;
};
node a[M];
int n,m,q;
vector<pair<int,int>> query[N];
vector<int> e[MAXM];
int f1[MAXM],f2[MAXM];
int vis[MAXM]={0},ans[M];
int root[MAXM];
inline bool cmp(node a,node b){
	return a.w>b.w;
}
int find1(int x){
	if(f1[x]!=x) f1[x]=find1(f1[x]);
	return f1[x];
}
int find2(int x){
	if(f2[x]!=x) f2[x]=find2(f2[x]);
	return f2[x];
}
void kruskal_build(){
	sort(a+1,a+m+1,cmp);
	for(int i=1;i<=200000;++i) f1[i]=i;
	for(int i=1;i<=n;++i) root[i]=1;
	for(int i=1;i<=m;++i){
		int r1=find1(a[i].u);
		int r2=find1(a[i].v);
		if(r1!=r2){
			e[r1].push_back(a[i].w);
			e[r2].push_back(a[i].w);
			e[a[i].w].push_back(r1);
			e[a[i].w].push_back(r2);
//			printf("%d-%d-%d\n",r1,r2,a[i].w);
			root[r1]=root[r2]=0;
			root[a[i].w]=1;
			f1[a[i].w]=f1[r1]=f1[r2]=a[i].w;
		}
	}
}
void Tarjan(int x){
	vis[x]=1;
	for(auto y:e[x]){
		if(!vis[y]){
			Tarjan(y);
			f2[y]=x;
		}
	}
	for(auto q:query[x]){
		int y=q.first,i=q.second;
		if(vis[y]) ans[i]=find2(y);
	}
}
int main(){
	scanf("%d%d",&n,&m);
	for(int i=1;i<=m;++i) scanf("%d%d%d",&a[i].u,&a[i].v,&a[i].w);
	for(int i=1;i<=m;++i) a[i].w+=10000;
	kruskal_build();
	scanf("%d",&q);
//	for(int i=1;i<=n;++i) printf("f(%d):%d\n",i,find1(i));
	for(int i=1;i<=q;++i){
		int a,b;
		scanf("%d%d",&a,&b);
		if(find1(a)!=find1(b)){
			ans[i]=-1;
			continue;
		}
		query[a].push_back({b,i});
		query[b].push_back({a,i});
	}
	for(int i=1;i<=200000;++i) f2[i]=i;
	for(int i=1;i<=200000;++i)
		if(root[i] && !vis[i]) {//printf(" *** %d\n",i);
			Tarjan(i);}
	for(int i=1;i<=q;++i) printf("%d\n",ans[i]==-1?ans[i]:ans[i]-10000);
}
2024/6/9 23:59
加载中...