Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 04a78ea

Browse files
feat: add solutions to lc problem: No.2204 (doocs#1994)
No.2204.Distance to a Cycle in Undirected Graph
1 parent f9d54b2 commit 04a78ea

File tree

9 files changed

+567
-5
lines changed

9 files changed

+567
-5
lines changed

‎solution/2200-2299/2204.Distance to a Cycle in Undirected Graph/README.md‎

Lines changed: 195 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -67,28 +67,221 @@
6767

6868
<!-- 这里可写通用的实现逻辑 -->
6969

70+
**方法一:拓扑排序**
71+
72+
我们可以先将 $edges$ 中的边转换成邻接表 $g,ドル其中 $g[i]$ 表示节点 $i$ 的所有邻接节点,用集合表示。
73+
74+
接下来,我们由外向内,逐层删除节点,直到最终只剩下一个环。具体做法如下:
75+
76+
我们先找出所有度为 1ドル$ 的节点,将这些节点从图中删除,如果删除后,其邻接节点的度变为 1ドル,ドル则将其加入队列 $q$ 中。过程中,我们按顺序记录下所有被删除的节点,记为 $seq$;并且,我们用一个数组 $f$ 记录每个节点相邻的且更接近环的节点,即 $f[i]$ 表示节点 $i$ 的相邻且更接近环的节点。
77+
78+
最后,我们初始化一个长度为 $n$ 的答案数组 $ans,ドル其中 $ans[i]$ 表示节点 $i$ 到环中任意节点的最小距离,初始时 $ans[i] = 0$。然后,我们从 $seq$ 的末尾开始遍历,对于每个节点 $i,ドル我们可以由它的相邻节点 $f[i]$ 得到 $ans[i]$ 的值,即 $ans[i] = ans[f[i]] + 1$。
79+
80+
遍历结束后,返回答案数组 $ans$ 即可。
81+
82+
时间复杂度 $O(n),ドル空间复杂度 $O(n)$。其中 $n$ 为节点数。
83+
84+
相似题目:
85+
86+
- [2603. 收集树中金币](/solution/2600-2699/2603.Collect%20Coins%20in%20a%20Tree/README.md)
87+
7088
<!-- tabs:start -->
7189

7290
### **Python3**
7391

7492
<!-- 这里可写当前语言的特殊实现逻辑 -->
7593

7694
```python
77-
95+
class Solution:
96+
def distanceToCycle(self, n: int, edges: List[List[int]]) -> List[int]:
97+
g = defaultdict(set)
98+
for a, b in edges:
99+
g[a].add(b)
100+
g[b].add(a)
101+
q = deque(i for i in range(n) if len(g[i]) == 1)
102+
f = [0] * n
103+
seq = []
104+
while q:
105+
i = q.popleft()
106+
seq.append(i)
107+
for j in g[i]:
108+
g[j].remove(i)
109+
f[i] = j
110+
if len(g[j]) == 1:
111+
q.append(j)
112+
g[i].clear()
113+
ans = [0] * n
114+
for i in seq[::-1]:
115+
ans[i] = ans[f[i]] + 1
116+
return ans
78117
```
79118

80119
### **Java**
81120

82121
<!-- 这里可写当前语言的特殊实现逻辑 -->
83122

84123
```java
124+
class Solution {
125+
public int[] distanceToCycle(int n, int[][] edges) {
126+
Set<Integer>[] g = new Set[n];
127+
Arrays.setAll(g, k -> new HashSet<>());
128+
for (var e : edges) {
129+
int a = e[0], b = e[1];
130+
g[a].add(b);
131+
g[b].add(a);
132+
}
133+
Deque<Integer> q = new ArrayDeque<>();
134+
for (int i = 0; i < n; ++i) {
135+
if (g[i].size() == 1) {
136+
q.offer(i);
137+
}
138+
}
139+
int[] f = new int[n];
140+
Deque<Integer> seq = new ArrayDeque<>();
141+
while (!q.isEmpty()) {
142+
int i = q.poll();
143+
seq.push(i);
144+
for (int j : g[i]) {
145+
g[j].remove(i);
146+
f[i] = j;
147+
if (g[j].size() == 1) {
148+
q.offer(j);
149+
}
150+
}
151+
}
152+
int[] ans = new int[n];
153+
while (!seq.isEmpty()) {
154+
int i = seq.pop();
155+
ans[i] = ans[f[i]] + 1;
156+
}
157+
return ans;
158+
}
159+
}
160+
```
161+
162+
### **C++**
85163

164+
```cpp
165+
class Solution {
166+
public:
167+
vector<int> distanceToCycle(int n, vector<vector<int>>& edges) {
168+
unordered_set<int> g[n];
169+
for (auto& e : edges) {
170+
int a = e[0], b = e[1];
171+
g[a].insert(b);
172+
g[b].insert(a);
173+
}
174+
queue<int> q;
175+
for (int i = 0; i < n; ++i) {
176+
if (g[i].size() == 1) {
177+
q.push(i);
178+
}
179+
}
180+
int f[n];
181+
int seq[n];
182+
int k = 0;
183+
while (!q.empty()) {
184+
int i = q.front();
185+
q.pop();
186+
seq[k++] = i;
187+
for (int j : g[i]) {
188+
g[j].erase(i);
189+
f[i] = j;
190+
if (g[j].size() == 1) {
191+
q.push(j);
192+
}
193+
}
194+
g[i].clear();
195+
}
196+
vector<int> ans(n);
197+
for (; k; --k) {
198+
int i = seq[k - 1];
199+
ans[i] = ans[f[i]] + 1;
200+
}
201+
return ans;
202+
}
203+
};
204+
```
205+
206+
### **Go**
207+
208+
```go
209+
func distanceToCycle(n int, edges [][]int) []int {
210+
g := make([]map[int]bool, n)
211+
for i := range g {
212+
g[i] = map[int]bool{}
213+
}
214+
for _, e := range edges {
215+
a, b := e[0], e[1]
216+
g[a][b] = true
217+
g[b][a] = true
218+
}
219+
q := []int{}
220+
for i := 0; i < n; i++ {
221+
if len(g[i]) == 1 {
222+
q = append(q, i)
223+
}
224+
}
225+
f := make([]int, n)
226+
seq := []int{}
227+
for len(q) > 0 {
228+
i := q[0]
229+
q = q[1:]
230+
seq = append(seq, i)
231+
for j := range g[i] {
232+
delete(g[j], i)
233+
f[i] = j
234+
if len(g[j]) == 1 {
235+
q = append(q, j)
236+
}
237+
}
238+
g[i] = map[int]bool{}
239+
}
240+
ans := make([]int, n)
241+
for k := len(seq) - 1; k >= 0; k-- {
242+
i := seq[k]
243+
ans[i] = ans[f[i]] + 1
244+
}
245+
return ans
246+
}
86247
```
87248

88249
### **TypeScript**
89250

90251
```ts
91-
252+
function distanceToCycle(n: number, edges: number[][]): number[] {
253+
const g: Set<number>[] = new Array(n).fill(0).map(() => new Set<number>());
254+
for (const [a, b] of edges) {
255+
g[a].add(b);
256+
g[b].add(a);
257+
}
258+
const q: number[] = [];
259+
for (let i = 0; i < n; ++i) {
260+
if (g[i].size === 1) {
261+
q.push(i);
262+
}
263+
}
264+
const f: number[] = Array(n).fill(0);
265+
const seq: number[] = [];
266+
while (q.length) {
267+
const i = q.pop()!;
268+
seq.push(i);
269+
for (const j of g[i]) {
270+
g[j].delete(i);
271+
f[i] = j;
272+
if (g[j].size === 1) {
273+
q.push(j);
274+
}
275+
}
276+
g[i].clear();
277+
}
278+
const ans: number[] = Array(n).fill(0);
279+
while (seq.length) {
280+
const i = seq.pop()!;
281+
ans[i] = ans[f[i]] + 1;
282+
}
283+
return ans;
284+
}
92285
```
93286

94287
### **...**

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /