LeetCode 题解工作台

从树中删除边的最小分数

存在一棵无向连通树,树中有编号从 0 到 n - 1 的 n 个节点, 以及 n - 1 条边。 给你一个下标从 0 开始的整数数组 nums ,长度为 n ,其中 nums[i] 表示第 i 个节点的值。另给你一个二维整数数组 edges ,长度为 n - 1 ,其中 edges[i] = [a …

category

4

题型

code_blocks

7

代码语言

hub

3

相关题

当前训练重点

困难 · 二分·树·traversal

bolt

答案摘要

我们记树的异或和为 ,即 $s = \text{nums}[0] \oplus \text{nums}[1] \oplus \ldots \oplus \text{nums}[n-1]$。 接下来,枚举 的每个点 作为树的根节点,将根节点与某个子节点 相连的边作为第一条被删除的边。这样我们就获得了两个连通块,我们记包含根节点 的连通块的异或和为 ,然后我们对包含根节点 的连通块进行 DF…

Interview AiBox logo

Interview AiBox 实时 AI 助手,陪你讲清 二分·树·traversal 题型思路

试试 AiBox 面试助手arrow_forward
description

题目描述

存在一棵无向连通树,树中有编号从 0n - 1n 个节点, 以及 n - 1 条边。

给你一个下标从 0 开始的整数数组 nums ,长度为 n ,其中 nums[i] 表示第 i 个节点的值。另给你一个二维整数数组 edges ,长度为 n - 1 ,其中 edges[i] = [ai, bi] 表示树中存在一条位于节点 aibi 之间的边。

删除树中两条 不同 的边以形成三个连通组件。对于一种删除边方案,定义如下步骤以计算其分数:

  1. 分别获取三个组件 每个 组件中所有节点值的异或值。
  2. 最大 异或值和 最小 异或值的 差值 就是这一种删除边方案的分数。
  • 例如,三个组件的节点值分别是:[4,5,7][1,9][3,3,3] 。三个异或值分别是 4 ^ 5 ^ 7 = 61 ^ 9 = 83 ^ 3 ^ 3 = 3 。最大异或值是 8 ,最小异或值是 3 ,分数是 8 - 3 = 5

返回在给定树上执行任意删除边方案可能的 最小 分数。

 

示例 1:

输入:nums = [1,5,5,4,11], edges = [[0,1],[1,2],[1,3],[3,4]]
输出:9
解释:上图展示了一种删除边方案。
- 第 1 个组件的节点是 [1,3,4] ,值是 [5,4,11] 。异或值是 5 ^ 4 ^ 11 = 10 。
- 第 2 个组件的节点是 [0] ,值是 [1] 。异或值是 1 = 1 。
- 第 3 个组件的节点是 [2] ,值是 [5] 。异或值是 5 = 5 。
分数是最大异或值和最小异或值的差值,10 - 1 = 9 。
可以证明不存在分数比 9 小的删除边方案。

示例 2:

输入:nums = [5,5,2,4,4,2], edges = [[0,1],[1,2],[5,2],[4,3],[1,3]]
输出:0
解释:上图展示了一种删除边方案。
- 第 1 个组件的节点是 [3,4] ,值是 [4,4] 。异或值是 4 ^ 4 = 0 。
- 第 2 个组件的节点是 [1,0] ,值是 [5,5] 。异或值是 5 ^ 5 = 0 。
- 第 3 个组件的节点是 [2,5] ,值是 [2,2] 。异或值是 2 ^ 2 = 0 。
分数是最大异或值和最小异或值的差值,0 - 0 = 0 。
无法获得比 0 更小的分数 0 。

 

提示:

  • n == nums.length
  • 3 <= n <= 1000
  • 1 <= nums[i] <= 108
  • edges.length == n - 1
  • edges[i].length == 2
  • 0 <= ai, bi < n
  • ai != bi
  • edges 表示一棵有效的树
lightbulb

解题思路

方法一:DFS + 子树异或和

我们记树的异或和为 ss,即 s=nums[0]nums[1]nums[n1]s = \text{nums}[0] \oplus \text{nums}[1] \oplus \ldots \oplus \text{nums}[n-1]

接下来,枚举 [0..n)[0..n) 的每个点 ii 作为树的根节点,将根节点与某个子节点 jj 相连的边作为第一条被删除的边。这样我们就获得了两个连通块,我们记包含根节点 ii 的连通块的异或和为 s1s_1,然后我们对包含根节点 ii 的连通块进行 DFS,计算出每个子树的异或和,记每次 DFS 计算出的子树异或和为 s2s_2。那么三个连通块的异或和分别为 ss1s \oplus s_1, s2s_2s1s2s_1 \oplus s_2。我们需要计算这三个异或和的最大值和最小值,记为 mx\textit{mx}mn\textit{mn},那么对于枚举的每一种情况,得到的分数为 mxmn\textit{mx} - \textit{mn}。求所有情况的最小值作为答案。

计算每个子树的异或和可以通过 DFS 实现。定义一个函数 dfs(i,fa)\text{dfs}(i, fa),表示从节点 ii 开始 DFS,而 fafa 是节点 ii 的父节点。函数返回值为以节点 ii 为根的子树的异或和。

时间复杂度 O(n2)O(n^2),空间复杂度 O(n)O(n)。其中 nn 是树的节点数。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
class Solution:
    def minimumScore(self, nums: List[int], edges: List[List[int]]) -> int:
        def dfs(i: int, fa: int) -> int:
            res = nums[i]
            for j in g[i]:
                if j != fa:
                    res ^= dfs(j, i)
            return res

        def dfs2(i: int, fa: int) -> int:
            nonlocal s, s1, ans
            res = nums[i]
            for j in g[i]:
                if j != fa:
                    s2 = dfs2(j, i)
                    res ^= s2
                    mx = max(s ^ s1, s2, s1 ^ s2)
                    mn = min(s ^ s1, s2, s1 ^ s2)
                    ans = min(ans, mx - mn)
            return res

        g = defaultdict(list)
        for a, b in edges:
            g[a].append(b)
            g[b].append(a)
        s = reduce(lambda x, y: x ^ y, nums)
        n = len(nums)
        ans = inf
        for i in range(n):
            for j in g[i]:
                s1 = dfs(i, j)
                dfs2(i, j)
        return ans
speed

复杂度分析

指标
时间complexity is O(n^2) due to evaluating each pair of edges for removal and computing the XOR differences using precomputed subtree values. Space complexity is O(n) to store the XOR of each subtree and track visited nodes during DFS.
空间O(n)
psychology

面试官常问的追问

外企场景
  • question_mark

    Look for a solution using binary-tree traversal and subtree state tracking.

  • question_mark

    Expect handling of XOR aggregation efficiently to avoid recalculation for each edge pair.

  • question_mark

    Check that the candidate properly identifies overlapping subtrees when removing edges.

warning

常见陷阱

外企场景
  • error

    Failing to precompute subtree XORs and recalculating for every edge pair.

  • error

    Double-counting nodes when the two removed edges affect nested subtrees.

  • error

    Ignoring edge cases where one component might contain only a single node.

swap_horiz

进阶变体

外企场景
  • arrow_right_alt

    Instead of XOR, compute sum differences among components after edge removals.

  • arrow_right_alt

    Apply the problem to a weighted tree where edge weights influence component value.

  • arrow_right_alt

    Generalize to removing k edges to create k+1 components with minimal XOR score.

help

常见问题

外企场景

从树中删除边的最小分数题解:二分·树·traversal | LeetCode #2322 困难