📅  最后修改于: 2023-12-03 15:07:34.734000             🧑  作者: Mango
该题目是一道关于树的题目,我们需要在给定的树中查找任意两个节点的距离,最后输出距离的和。以下是题目的具体描述:
给定一个树,其中树结构由无序对 u 和 v 的值以及它们之间的距离组成。现在,假设要从树中找到两个节点之间的距离并返回它们的总和。
输入包含一个整数 T,表示测试用例的数量。然后是 T 个测试用例,每个测试用例都有以下格式:
第一行包含一个整数 N,表示树中节点的数量。
接下来的 N-1 行包含无序对 u 和 v 的值,以及它们之间的距离。
对于每个测试用例,都要在新行上输出总和。
1
3
1 2 1
2 3 2
6
在上面的示例中,有以下两个节点对:
因此,输出总和为 6。
该题目要求我们求出树中任意两个节点之间的距离并求和,我们可以考虑使用DFS(深度优先搜索)的方式来遍历所有的节点对,然后利用最近公共祖先算法来求每个节点对之间的距离。
def dfs(u, p, dist):
# u:当前节点
# p:u 的父节点
# dist:u 到根节点的距离
global ans
for v, w in tree[u]:
if v != p:
dfs(v, u, dist + w)
ans += (dist + w) * (n - (size[v] if v != p else size[u]))
# 计算子树大小
def calc_size(u, p):
size[u] = 1
for v, w in tree[u]:
if v != p:
calc_size(v, u)
size[u] += size[v]
# 计算 LCA
def calc_lca(u, v):
if depth[u] < depth[v]:
u, v = v, u
while depth[u] > depth[v]:
u = parent[u]
while u != v:
u = parent[u]
v = parent[v]
return u
# 初始化
def init():
global ans, tree, size, parent, depth
ans = 0
tree = [[] for i in range(n+1)]
size = [0] * (n+1)
parent = [0] * (n+1)
depth = [0] * (n+1)
# 处理每个测试用例
for _ in range(T):
n = int(input())
init()
for i in range(n-1):
u, v, w = map(int, input().split())
tree[u].append((v, w))
tree[v].append((u, w))
calc_size(1, 0)
for u in range(1, n+1):
for v, w in tree[u]:
if v != parent[u]:
parent[v] = u
depth[v] = depth[u] + 1
for u in range(1, n+1):
for v, w in tree[u]:
if v != parent[u]:
p = calc_lca(u, v)
ans += w * (size[v] if v != p else n - size[u])
print(ans)
该题目涉及到了树的相关算法,需要我们将树中的节点遍历一遍,并计算每个节点之间的距离。同时,需要注意算法中的一些细节问题,如计算节点子树大小、LCA 等。