1AC+6WA+3RE求调
查看原帖
1AC+6WA+3RE求调
194465
Evan_S楼主2021/7/13 17:16
#include<iostream>
#include<vector>
#include<cstring>
using namespace std;

vector<long long> G[100010];
long long fa[100010];
long long dp[100010];
long long sz[100010];
long long sn[100010];
long long dfn[100010];
long long tp[100010];
long long tree[100010];
long long a[100010];
long long val[400010];
long long flag[400010];
long long cnt, n, m, root;
long long dfs(long long u)
{
	dp[u] = dp[fa[u]] + 1;
	sz[u] = 1;
	for(long long v : G[u])
	{
		if(fa[u] != v)
		{
			fa[v] = u;
			dfs(v);
			sz[u] += sz[v];
			if(sz[v] > sz[sn[u]])
			{
				sn[u] = v;
			}
		}
	}
	return 0;
}

long long dfs2(long long u, long long t)
{
	dfn[u] = ++cnt;
	a[cnt] = tree[u];
	tp[u] = t;
	if(sn[u])
	{
		dfs2(sn[u], t);
	}
	for(long long v : G[u])
	{
		if(fa[u] != v && sn[u] != v)
		{
			dfs2(v, v);
		}
	}
	return 0;
}

long long pushdown(long long o, long long l, long long r)
{
	if(flag[o])
	{
		val[o << 1] = flag[o];
		val[o << 1 | 1] = flag[o];
		flag[o << 1] = flag[o];
		flag[o << 1 | 1] = flag[o];
		flag[o] = 0;
	}
}

long long build(long long o, long long l, long long r)
{
	if(l == r)
	{
		val[o] = a[l];
		return 0;
	}
	long long mid = l + r >> 1;
	build(o << 1, l, mid);
	build(o << 1 | 1, mid + 1, r);
	val[o] = min(val[o << 1], val[o << 1 | 1]);
	return 0;
}

long long set(long long o, long long l, long long r, long long s, long long t, long long k)
{
	if(s <= l && r <= t)
	{
		val[o] = k;
		flag[o] = k;
		return 0;
	}
	pushdown(o, l, r);
	long long mid = l + r >> 1;
	if(s <= mid)
	{
		set(o << 1, l, mid, s, t, k);
	}
	if(mid < t)
	{
		set(o << 1 | 1, mid + 1, r, s, t, k);
	}
	val[o] = min(val[o << 1], val[o << 1 | 1]);
	return 0;
}

long long query(long long o, long long l, long long r, long long s, long long t)
{
	if(s <= l && r <= t)
	{
		return val[o];
	}
	pushdown(o, l, r);
	long long mid = l + r >> 1;
	long long ans = 21474836470000;
	if(s <= mid)
	{
		ans = min(ans, query(o << 1, l, mid, s, t));
	}
	if(mid < t)
	{
		ans = min(ans, query(o << 1 | 1, mid + 1, r, s, t));
	}
	return ans;
}

long long setpath(long long u, long long v, long long k)
{
	while(tp[u] != tp[v])
	{  
		if(dp[tp[u]] < dp[tp[v]])  
		{
			swap(u, v);
		}
		set(1, 1, n, dfn[tp[u]], dfn[u], k);
		u = fa[tp[u]]; 
	}
	if(dp[u] > dp[v])
	{
		swap(u, v);
	}
	set(1, 1, n, dfn[u], dfn[v], k);
	return 0;
}

long long querytree(long long u)
{
	return query(1, 1, n, dfn[u], dfn[u] + sz[u] - 1);
}

long long find(long long u)
{
	long long now = root;
	while(tp[now] != tp[u])
	{
		if(fa[tp[now]] == u)
		{
			return tp[now];
		}
		now = fa[tp[now]];
	}
	return sn[u];
}

int main()
{
	scanf("%lld%lld", &n, &m);
	for(long long i = 1; i < n; i++)
	{
		long long u, v;
		scanf("%lld%lld", &u, &v);
		G[u].push_back(v);
		G[v].push_back(u);
	}
	for(long long i = 1; i <= n; i++)
	{
		scanf("%lld", &tree[i]);
	}
	dfs(1);
	dfs2(1, 1);
	build(1, 1, n);
	scanf("%lld", &root);
	for(long long i = 1; i <= m; i++)
	{
		long long op;
		scanf("%lld", &op);
		if(op == 1)
		{
			scanf("%lld", &root);
		}
		if(op == 2)
		{
			long long u, v, w;
			scanf("%lld%lld%lld", &u, &v, &w);
			setpath(u, v, w);
		}
		else
		{
			long long u;
			scanf("%lld", &u);
			if(u == root)
			{
				printf("%lld\n", val[1]);
			}
			else if(dfn[root] <= dfn[u] || dfn[u] + sz[u] <= dfn[root])
			{
				printf("%lld\n", querytree(u));
			}
			else
			{
				long long x = find(u);
				long long ans = query(1, 1, n, 1, dfn[x] - 1);
				if(dfn[x] + sz[x] - 1 != n)
				{
					ans = min(ans, query(1, 1, n, dfn[x] + sz[x], n));
				}
				printf("%lld\n", ans);
			}
		}
	}
}
2021/7/13 17:16
加载中...