倍增求条
查看原帖
倍增求条
530468
_determination_楼主2023/11/25 15:32

RT,今天模拟赛出原,但是挂了(

求条

code:

#include<bits/stdc++.h>
using namespace std;
#define int long long
#define inf 1e18
struct abc{
	int u,v,val;
}e[50010];
int f[10010];
int cmp(abc p,abc q)
{
	return p.val >q.val;
}
int find(int x)
{
	if(f[x]==x)
	{
		return x;
	}
	return f[x]=find(f[x]);
}
vector<int>edge[10010];
vector<int>eval[10010];
int fa[10010][20];
int ans[10010][20];
int h[10010];
void dfs(int x)
{
	for ( int i = 0 ; i < edge[x].size() ; i++ )
	{
		if(edge[x][i]==fa[x][0])
		{
			continue;
		}
		int v=edge[x][i];
		h[v]=h[x]+1;
		fa[v][0]=x;
		ans[v][0]=eval[x][i];
		for ( int j = 1 ; j < 20 ; j++ )
		{
			fa[v][j]=fa[fa[v][j-1]][j-1];
			ans[v][j]=min(ans[fa[v][j-1]][j-1],ans[v][j-1]);
		}
		dfs(v);
	}
}
signed main()
{
    int n,m;
    cin >> n >> m;
    for ( int i = 1 ; i <= m ; i++ )
    {
    	cin >> e[i].u >> e[i].v >> e[i].val;
	}
	sort(e+1,e+m+1,cmp);
	for ( int i = 1 ; i <= n ; i++ )
	{
		f[i]=i;
	}
	for ( int i = 1 ; i <= m ; i++ )
	{
		int fau=find(e[i].u),fav=find(e[i].v);
		int u=e[i].u,v=e[i].v;
		if(fau!=fav)
		{
			edge[u].push_back(v);
			edge[v].push_back(u);
			eval[u].push_back(e[i].val);
			eval[v].push_back(e[i].val);
			f[fau]=fav;
//			cout << u << " " << v << endl;
		}
	}
	for ( int i = 1 ; i <= n ; i++ )
	{
		if(fa[i][0]==0)
		{
			h[i]=1;
			for ( int j = 0 ; j < 20 ; j++ )
			{
				fa[i][j]=i;
				ans[i][j]=inf;
			}
			dfs(i);
		}
	}
	int q;
	cin >> q;
	while(q--)
	{
		int x,y;
		cin >> x>>y;
		if(find(x)!=find(y))
		{
			cout << -1 << endl;
			continue;
		}
		if(h[x]<h[y])
		{
			swap(x,y);
		}
		int k=19;
		int cnt=inf;
		while(h[x]>h[y])
		{
			int fat=fa[x][k];
			if(h[fat]<=h[y])
			{
				cnt=min(cnt,ans[x][k]);
				x=fat;
			}
			k--;
		}
		k=19;
		while(x!=y)
		{
			int fax=fa[x][k],fay=fa[y][k];
			if(fax!=fay||k==0)
			{
				cnt=min(cnt,ans[x][k]);
				x=fax;
				cnt=min(cnt,ans[y][k]);
				y=fay;
			}
			if(k!=0)
			{
				k--;
			}
		}
		cout << cnt << endl;
	}
    return 0;
}

Link

2023/11/25 15:32
加载中...