Source code for titan_pylib.graph.dfs_tree

 1from titan_pylib.others.antirec import antirec
 2
 3
[docs] 4class DFSTree: 5 6 def __init__(self, G: list[list[int]]) -> None: 7 self.n = len(G) 8 self.G = G 9 self.order = [-1] * self.n 10 self.low = [self.n] * self.n 11 self.par = [-1] * self.n 12 self.dfs_forest = [[] for _ in range(self.n)] 13 self._calc_lowlink() 14 15 def _calc_lowlink(self) -> None: 16 t = 0 17 order, low, par, dfs_forest = self.order, self.low, self.par, self.dfs_forest 18 G = self.G 19 20 @antirec 21 def dfs(v: int, p: int = -1): 22 nonlocal t 23 par[v] = p 24 order[v] = t 25 low[v] = t 26 t += 1 27 seen_p = False 28 for x in G[v]: 29 if x == p and not seen_p: 30 seen_p = True 31 continue 32 if order[x] == -1: 33 dfs_forest[v].append(x) 34 dfs_forest[x].append(v) 35 yield dfs(x, v) 36 low[v] = min(low[v], low[x]) 37 else: 38 low[v] = min(low[v], order[x]) 39 yield 40 41 for v in range(self.n): 42 if order[v] == -1: 43 dfs(v) 44
[docs] 45 def get_bridge(self) -> list[tuple[int, int]]: 46 order, low, par, dfs_forest = self.order, self.low, self.par, self.dfs_forest 47 bridge = [] 48 for v in range(self.n): 49 if par[v] != -1: 50 continue 51 todo = [v] 52 while todo: 53 v = todo.pop() 54 for x in dfs_forest[v]: 55 if x == par[v]: 56 continue 57 if order[v] < low[x]: 58 bridge.append((min(v, x), max(v, x))) 59 todo.append(x) 60 return bridge
61
[docs] 62 def get_two_edge_connected_components(self): 63 """二辺連結成分分解""" 64 order, low, par, dfs_forest = self.order, self.low, self.par, self.dfs_forest 65 ids = [-1] * self.n 66 E = [] 67 idx = 0 68 for v in range(self.n): 69 if par[v] != -1: 70 continue 71 ids[v] = idx 72 todo = [v] 73 while todo: 74 v = todo.pop() 75 for x in dfs_forest[v]: 76 if x == par[v]: 77 continue 78 if order[v] < low[x]: 79 idx += 1 80 ids[x] = idx 81 E.append((ids[v], idx)) 82 else: 83 ids[x] = ids[v] 84 todo.append(x) 85 idx += 1 86 gropus = [[] for _ in range(idx)] 87 F = [[] for _ in range(idx)] 88 for v in range(self.n): 89 gropus[ids[v]].append(v) 90 for u, v in E: 91 F[u].append(v) 92 F[v].append(u) 93 return ids, gropus, F