记录编号 577549 评测结果 AAAAAAAAAAAAAAAAAAAAAAAAA
题目名称 [CSP 2022S]数据传输 最终得分 100
用户昵称 Gravataryrtiop 是否通过 通过
代码语言 C++ 运行时间 16.425 s
提交时间 2022-11-09 10:52:10 内存使用 0.00 MiB
显示代码纯文本
// Problem: P8820 [CSP-S 2022] 数据传输
// Contest: Luogu
// URL: https://www.luogu.com.cn/problem/P8820
// Memory Limit: 1 MB
// Time Limit: 3000 ms
// 
// Powered by CP Editor (https://cpeditor.org)

#include <bits/stdc++.h>
#define pb emplace_back
using i64 = long long;

const i64 INF = 1e16;
const int maxn = 2e5 + 5;
std::vector<int> G[maxn];
int n,m;
int f[maxn][20],lg[maxn],dep[maxn];
i64 d[maxn],val[maxn],b[maxn];

void dfs(int u,int fa) {
	d[u] = d[fa] + val[u];
	for(auto& v : G[u]) {
		if(v == fa)continue ;
		dep[v] = dep[u] + 1;
		f[v][0] = u;
		for(int k = 1;(1 << k) <= dep[v];++ k)
			f[v][k] = f[f[v][k - 1]][k - 1];
		dfs(v , u);
	}
	return ;
}

int LCA(int u,int v) {
	if(dep[u] < dep[v])std::swap(u , v);
	for(int k = lg[dep[u]];~ k;-- k) {
		if(dep[u] - (1 << k) >= dep[v]) {
			u = f[u][k];
		}
		if(u == v)return u;
	}
	for(int k = lg[dep[u]];~ k;-- k) {
		if(f[u][k] != f[v][k]) {
			u = f[u][k];
			v = f[v][k];
		}
	}
	return f[u][0];
}

namespace subtask_1 {
	int main() {
		while(m --) {
			int u,v;
			scanf("%d %d",&u,&v);
			int t = LCA(u , v);
			printf("%lld\n",d[u] + d[v] - d[t] - d[f[t][0]]);
		}
		return 0;
	}
}

namespace subtask_2 {
	struct matrix {
		i64 g[2][2];
		matrix() {
			g[0][0] = g[0][1] = g[1][0] = g[1][1] = INF;
		}
		void init() {
			g[0][0] = g[0][1] = g[1][0] = g[1][1] = INF;
			return ;
		}
		matrix operator * (const matrix& p)const {
			matrix a;
			for(int q = 0;q < 2;++ q) {
				for(int i = 0;i < 2;++ i) {
					for(int j = 0;j < 2;++ j) {
						a.g[i][j] = std::min(a.g[i][j] , g[i][q] + p.g[q][j]);
					}
				}
			}
			return a;
		}
	}S[maxn][18];
	
	void DFS(int u,int fa) {
		for(auto& v : G[u]) {
			if(v == fa)continue ;
			S[v][0].g[0][0] = val[v];
			S[v][0].g[0][1] = 0;
			S[v][0].g[1][0] = val[v];
			S[v][0].g[1][1] = INF;
			for(int k = 1;(1 << k) <= dep[v];++ k)
				S[v][k] = S[v][k - 1] * S[f[v][k - 1]][k - 1];
			DFS(v , u);
		}
		return ;
	}
	
	int main() {
		S[1][0].g[0][0] = val[1];
		S[1][0].g[0][1] = 0;
		S[1][0].g[1][0] = val[1];
		S[1][0].g[1][1] = INF;
		DFS(1 , 0);
		while(m --) {
			int u,v,t;
			scanf("%d %d",&u,&v);
			if(u == v) {
				printf("%lld\n",val[u]);
				continue ;
			}
			t = LCA(u , v);
			i64 ans = INF;
			matrix F,P;
			F.g[0][0] = val[u];
			P.g[0][0] = val[v];
			int x = f[u][0];
			if(u != t) {
				for(int k = lg[dep[x]];~ k;-- k) {
					if(dep[x] < dep[t])break ;
					if(dep[f[x][k]] >= dep[t]) {
						F = F * S[x][k];
						x = f[x][k];
					}
				}
				while(dep[x] >= dep[t])F = F * S[x][0],x = f[x][0];
			}
			if(v != t) {
				x = f[v][0];
				for(int k = lg[dep[x]];~ k;-- k) {
					if(dep[x] < dep[t])break ;
					if(dep[f[x][k]] >= dep[t]) {
						P = P * S[x][k];
						x = f[x][k];
					}
				}
				while(dep[x] >= dep[t])P = P * S[x][0],x = f[x][0];
			}
			ans = std::min(F.g[0][0] + P.g[0][0] - val[t] , F.g[0][1] + P.g[0][1]);
			printf("%lld\n",ans);
		}
		return 0;
	}
}

namespace subtask_3 {
	struct matrix {
		i64 g[5][5];
		matrix() {
			for(int i = 0;i < 5;++ i)
				for(int j = 0;j < 5;++ j)
					g[i][j] = INF;
		}
		void init() {
			for(int i = 0;i < 5;++ i)
				for(int j = 0;j < 5;++ j)
					g[i][j] = INF;
		}
		matrix operator * (const matrix& p)const {
			matrix c;
			for(int k = 0;k < 5;++ k)
				for(int i = 0;i < 5;++ i)
					for(int j = 0;j < 5;++ j)
						c.g[i][j] = std::min(c.g[i][j] , g[i][k] + p.g[k][j]);
			return c;
		}
	}S[maxn][18];
	
	void getinit(int u) {
		S[u][0].g[0][0] = val[u];
		S[u][0].g[0][1] = 0;
		S[u][0].g[0][3] = b[u];
		S[u][0].g[1][0] = val[u];
		S[u][0].g[1][2] = 0;
		S[u][0].g[1][3] = b[u];
		S[u][0].g[2][0] = val[u];
		S[u][0].g[3][0] = val[u];
		S[u][0].g[3][3] = b[u];
		S[u][0].g[3][4] = 0;
		S[u][0].g[4][0] = val[u];
		return ;
	}
	
	void DFS(int u,int fa) {
		for(auto& v : G[u]) {
			if(v == fa)continue ;
			getinit(v);
			for(int k = 1;(1 << k) <= dep[v];++ k)
				S[v][k] = S[v][k - 1] * S[f[v][k - 1]][k - 1];
			DFS(v , u);
		}
		return ;
	}
	
	int main() {
		for(int i = 1;i <= n;++ i) {
			b[i] = INF;
			for(auto& v : G[i]) {
				b[i] = std::min(b[i] , val[v]);
			}
		}
		
		getinit(1);
		DFS(1 , 0);
		
		while(m --) {
			int u,v,t;
			scanf("%d %d",&u,&v);
			if(u == v) {
				printf("%lld\n",val[u]);
				continue ;
			}
			t = LCA(u , v);
			i64 ans = INF;
			matrix F,P;
			F.g[0][0] = val[u];
			P.g[0][0] = val[v];
			int x = f[u][0];
			if(u != t) {
				for(int k = lg[dep[x]];~ k;-- k) {
					if(dep[x] < dep[t])break ;
					if(dep[f[x][k]] >= dep[t]) {
						F = F * S[x][k];
						x = f[x][k];
					}
				}
				while(dep[x] >= dep[t])F = F * S[x][0],x = f[x][0];
			}
			if(v != t) {
				x = f[v][0];
				for(int k = lg[dep[x]];~ k;-- k) {
					if(dep[x] < dep[t])break ;
					if(dep[f[x][k]] >= dep[t]) {
						P = P * S[x][k];
						x = f[x][k];
					}
				}
				while(dep[x] >= dep[t])P = P * S[x][0],x = f[x][0];
			}
			ans = std::min(ans , F.g[0][0] + P.g[0][0] - val[t]);
			ans = std::min(ans , F.g[0][3] + P.g[0][3] - b[t]);
			ans = std::min(ans , F.g[0][1] + P.g[0][1]);
			ans = std::min(ans , F.g[0][1] + P.g[0][2]);
			ans = std::min(ans , F.g[0][1] + P.g[0][4]);
			ans = std::min(ans , F.g[0][4] + P.g[0][1]);
			ans = std::min(ans , F.g[0][2] + P.g[0][1]);
			printf("%lld\n",ans);
		}
		return 0;
	}
}

int k;

int main() {
	freopen("csp2022_transmit.in","r",stdin);
	freopen("csp2022_transmit.out","w",stdout);
	scanf("%d %d %d",&n,&m,&k);
	for(int i = 1;i <= n;++ i)
		scanf("%lld",&val[i]);
	for(int i = 1;i < n;++ i) {
		int u,v;
		scanf("%d %d",&u,&v);
		G[u].pb(v);
		G[v].pb(u);
	}
	
	dep[0] = -1;
	for(int i = 2;i <= n;++ i)
		lg[i] = lg[i >> 1] + 1;
	dfs(1 , 0);
	
	if(k == 1) {
		subtask_1::main();
		return 0;
	}
	if(k == 2) {
		subtask_2::main();
		return 0;
	}
	else subtask_3::main();
	return 0;
}