Skip to content

Commit 9af1717

Browse files
committed
feat: add solutions for lc No.3910
1 parent 6eefb8f commit 9af1717

7 files changed

Lines changed: 583 additions & 8 deletions

File tree

solution/3900-3999/3910.Count Connected Subgraphs with Even Node Sum/README.md

Lines changed: 198 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -146,32 +146,226 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3900-3999/3910.Co
146146

147147
<!-- solution:start -->
148148

149-
### 方法一
149+
### 方法一:二进制枚举 + DFS
150+
151+
我们注意到,题目中节点的数量不超过 $13$,因此我们可以枚举节点的所有非空子集 $s$,对于每个子集,我们可以计算出其节点值的总和,并判断其诱导子图是否连通。
152+
153+
具体地,我们可以使用一个整数 $sub$ 来表示子集 $s$,其中 $sub$ 的第 $i$ 位为 $1$ 表示节点 $i$ 在子集中,为 $0$ 表示节点 $i$ 不在子集中。对于每个子集,我们首先计算出其节点值的总和,如果总和为奇数,则跳过该子集;否则,我们使用 DFS 来判断其诱导子图是否连通。我们可以使用一个整数 $vis$ 来表示已经访问过的节点,初始时 $vis$ 的第 $i$ 位为 $1$ 表示节点 $i$ 不在子集中,为 $0$ 表示节点 $i$ 在子集中。我们从子集 $s$ 中的任意一个节点开始 DFS,访问其所有相邻节点,并将访问过的节点在 $vis$ 中标记为 $1$。最后,如果 $vis$ 的所有位都为 $1$,则说明子集 $s$ 的诱导子图是连通的,我们将答案加 $1$。
154+
155+
时间复杂度 $O(2^n \times (n + m))$,空间复杂度 $O(n + m)$,其中 $n$ 和 $m$ 分别是节点数和边数。
150156

151157
<!-- tabs:start -->
152158

153159
#### Python3
154160

155161
```python
156-
162+
class Solution:
163+
def evenSumSubgraphs(self, nums: list[int], edges: list[list[int]]) -> int:
164+
n = len(nums)
165+
g = [[] for _ in range(n)]
166+
for u, v in edges:
167+
g[u].append(v)
168+
g[v].append(u)
169+
m = (1 << n) - 1
170+
ans = 0
171+
for sub in range(1, m + 1):
172+
s = sum(x for i, x in enumerate(nums) if sub >> i & 1)
173+
if s % 2:
174+
continue
175+
vis = m ^ sub
176+
177+
def dfs(u: int) -> None:
178+
nonlocal vis
179+
vis |= 1 << u
180+
for v in g[u]:
181+
if (vis >> v & 1) == 0:
182+
dfs(v)
183+
184+
dfs(sub.bit_length() - 1)
185+
if vis == m:
186+
ans += 1
187+
return ans
157188
```
158189

159190
#### Java
160191

161192
```java
162-
193+
class Solution {
194+
private int vis;
195+
private int m;
196+
private List<Integer>[] g;
197+
198+
public int evenSumSubgraphs(int[] nums, int[][] edges) {
199+
int n = nums.length;
200+
g = new List[n];
201+
Arrays.setAll(g, k -> new ArrayList<>());
202+
for (int[] e : edges) {
203+
g[e[0]].add(e[1]);
204+
g[e[1]].add(e[0]);
205+
}
206+
m = (1 << n) - 1;
207+
int ans = 0;
208+
for (int sub = 1; sub <= m; sub++) {
209+
int s = 0;
210+
for (int i = 0; i < n; i++) {
211+
if (((sub >> i) & 1) == 1) {
212+
s += nums[i];
213+
}
214+
}
215+
if (s % 2 != 0) {
216+
continue;
217+
}
218+
vis = m ^ sub;
219+
dfs(Integer.numberOfTrailingZeros(sub));
220+
if (vis == m) {
221+
ans++;
222+
}
223+
}
224+
return ans;
225+
}
226+
227+
private void dfs(int u) {
228+
vis |= 1 << u;
229+
for (int v : g[u]) {
230+
if (((vis >> v) & 1) == 0) {
231+
dfs(v);
232+
}
233+
}
234+
}
235+
}
163236
```
164237

165238
#### C++
166239

167240
```cpp
168-
241+
class Solution {
242+
public:
243+
int evenSumSubgraphs(vector<int>& nums, vector<vector<int>>& edges) {
244+
int n = nums.size();
245+
vector<vector<int>> g(n);
246+
for (auto& e : edges) {
247+
g[e[0]].push_back(e[1]);
248+
g[e[1]].push_back(e[0]);
249+
}
250+
int m = (1 << n) - 1;
251+
int ans = 0;
252+
int vis;
253+
254+
auto dfs = [&](this auto dfs, int u) -> void {
255+
vis |= 1 << u;
256+
for (int v : g[u]) {
257+
if (((vis >> v) & 1) == 0) {
258+
dfs(v);
259+
}
260+
}
261+
};
262+
263+
for (int sub = 1; sub <= m; sub++) {
264+
int s = 0;
265+
for (int i = 0; i < n; i++) {
266+
if ((sub >> i) & 1) {
267+
s += nums[i];
268+
}
269+
}
270+
if (s % 2 != 0) {
271+
continue;
272+
}
273+
vis = m ^ sub;
274+
dfs(31 - __builtin_clz(sub));
275+
if (vis == m) {
276+
ans++;
277+
}
278+
}
279+
return ans;
280+
}
281+
};
169282
```
170283

171284
#### Go
172285

173286
```go
287+
func evenSumSubgraphs(nums []int, edges [][]int) int {
288+
n := len(nums)
289+
g := make([][]int, n)
290+
for _, e := range edges {
291+
g[e[0]] = append(g[e[0]], e[1])
292+
g[e[1]] = append(g[e[1]], e[0])
293+
}
294+
m := (1 << n) - 1
295+
ans := 0
296+
var vis int
297+
298+
var dfs func(int)
299+
dfs = func(u int) {
300+
vis |= 1 << u
301+
for _, v := range g[u] {
302+
if (vis >> v & 1) == 0 {
303+
dfs(v)
304+
}
305+
}
306+
}
307+
308+
for sub := 1; sub <= m; sub++ {
309+
s := 0
310+
for i := 0; i < n; i++ {
311+
if sub>>i&1 == 1 {
312+
s += nums[i]
313+
}
314+
}
315+
if s%2 != 0 {
316+
continue
317+
}
318+
vis = m ^ sub
319+
dfs(bits.Len(uint(sub)) - 1)
320+
if vis == m {
321+
ans++
322+
}
323+
}
324+
return ans
325+
}
326+
```
174327

328+
#### TypeScript
329+
330+
```ts
331+
function evenSumSubgraphs(nums: number[], edges: number[][]): number {
332+
const n = nums.length;
333+
const g: number[][] = Array.from({ length: n }, () => []);
334+
for (const [u, v] of edges) {
335+
g[u].push(v);
336+
g[v].push(u);
337+
}
338+
const m = (1 << n) - 1;
339+
let ans = 0;
340+
let vis = 0;
341+
342+
const dfs = (u: number): void => {
343+
vis |= 1 << u;
344+
for (const v of g[u]) {
345+
if (((vis >> v) & 1) === 0) {
346+
dfs(v);
347+
}
348+
}
349+
};
350+
351+
for (let sub = 1; sub <= m; sub++) {
352+
let s = 0;
353+
for (let i = 0; i < n; i++) {
354+
if ((sub >> i) & 1) {
355+
s += nums[i];
356+
}
357+
}
358+
if (s % 2 !== 0) {
359+
continue;
360+
}
361+
vis = m ^ sub;
362+
dfs(sub.toString(2).length - 1);
363+
if (vis === m) {
364+
ans++;
365+
}
366+
}
367+
return ans;
368+
}
175369
```
176370

177371
<!-- tabs:end -->

0 commit comments

Comments
 (0)