給定乙個無向、連通的樹。樹中有 n 個標記為 0...n-1 的節點以及 n-1 條邊 。第 i 條邊連線節點 edges[i][0] 和 edges[i][1] 。
返回乙個表示節點 i 與其他所有節點距離之和的列表 ans。
示例 1:
輸入: n = 6, edges = [[0,1],[0,2],[2,3],[2,4],[2,5]]
輸出: [8,12,6,10,10,10]
解釋:如下為給定的樹的示意圖:
0/ \
1 2
/|\3 4 5
我們可以計算出 dist(0,1) + dist(0,2) + dist(0,3) + dist(0,4) + dist(0,5)
也就是 1 + 1 + 2 + 2 + 2 = 8。 因此,answer[0] = 8,以此類推。
1.暴力dfs,加不了記憶化
2.遞迴的dfs,可加記憶化
class solution:
def sumofdistancesintree(self, n: int, edges: list[list[int]]) -> list[int]:
graph=collections.defaultdict(list)
for e in edges:
res=
def dfs(node,c):
self.cnt+=c
for n in graph[node]:
if n not in visited:
visited.add(n)
dfs(n,c+1)
for i in range(n):
visited=set([i])
self.cnt=0
dfs(i,0)
return res
class solution:
def sumofdistancesintree(self, n: int, edges: list[list[int]]) -> list[int]:
from functools import lru_cache
@lru_cache(none)
def dp(u, fa): # dp(u, fa) 表示斷開 u->fa 這條邊的情況下,以 u 為根的樹的距離和以及這顆樹的大小。
dis, sz = 0, 0
for v in g[u]:
if v == fa: continue
vdis, vsz = dp(v, u)
dis += vdis
sz += vsz
return (dis + sz, sz + 1)
g = [ for _ in range(n)]
for u, v in edges:
return [dp(u, -1)[0] for u in range(n)]
leetcode 834樹中距離之和
這道題考察的是樹形dp,需要兩次dfs。第一次dfs建立樹形結構,並求得根節點到其他點的距離和。第二次dfs是通過交換根節點,獲得以其他點作為根節點的距離和。對於根節點u和它的子結點v,u與其他節點的距離和dp u 可以表示為 d p v sz v sigma dp v sz v dp v sz v...
LeetCode 834 樹中距離之和
原題目 思路 採用樹形動態規劃的思想。對於每乙個節點來說,所有節點到他的距離之和的狀態轉移方程為 其中dp v 代表以v為根的所有節點到他的距離,sz v 表示已v為根的子樹節點的數量。dp u dp u dp v sz v sz u sz u sz v dp v dp v dp u sz u sz...
leetcode 834 樹中距離之和
題目鏈結 給定乙個無向 連通的樹。樹中有 n 個標記為 0 n 1 的節點以及 n 1 條邊 第 i 條邊連線節點 edges i 0 和 edges i 1 返回乙個表示節點 i 與其他所有節點距離之和的列表 ans。說明 1 n 10000 class solution if n 2 vecto...