mirror of
https://gitlab.com/game-loader/hugo.git
synced 2025-04-19 21:42:07 +08:00
leetcode update
This commit is contained in:
parent
27449e6eff
commit
e93cb2c0e6
@ -22374,3 +22374,121 @@ public:
|
||||
}
|
||||
};
|
||||
```
|
||||
## day327 2025-01-30
|
||||
### 2493. Divide Nodes Into the Maximum Number of Groups
|
||||
You are given a positive integer n representing the number of nodes in an undirected graph. The nodes are labeled from 1 to n.
|
||||
|
||||
You are also given a 2D integer array edges, where edges[i] = [ai, bi] indicates that there is a bidirectional edge between nodes ai and bi. Notice that the given graph may be disconnected.
|
||||
|
||||
Divide the nodes of the graph into m groups (1-indexed) such that:
|
||||
|
||||
Each node in the graph belongs to exactly one group.
|
||||
For every pair of nodes in the graph that are connected by an edge [ai, bi], if ai belongs to the group with index x, and bi belongs to the group with index y, then |y - x| = 1.
|
||||
Return the maximum number of groups (i.e., maximum m) into which you can divide the nodes. Return -1 if it is impossible to group the nodes with the given conditions.
|
||||
|
||||

|
||||
|
||||
### 题解
|
||||
本题是一道难题,也是看了题解才明白如何解决该题。
|
||||
|
||||
要想解决该题,首先要观察到一个非常重要的现象,即任何可以被分成两个以上不同组的连通图中的所有节点,最终都可以通过合并归类到两个组中。如当前有四个不同的组,则一定可以将第四组和第二组合并到一起,因为二者都和第三组相连,二第四组和第一组又无关,因此合并后一定满足条件,现在变为三组,同理可以将第三组和第一组合并,这样就变成了两组,由此可以发现,只要图能够被分为两组,且只有位于不同组的节点之间有边,该图就可以被分成不同的组,即图必须是一个二分图。
|
||||
|
||||
判断二分图的常用办法即涂色法,即将图中节点分为两组后,每组中的全部节点都是同一种颜色。在实际实现时,只需将每个节点的相邻节点都涂为和当前节点不同的颜色即可,一旦出现冲突即说明该图不是二分图。
|
||||
|
||||
第二个难点是观察到是二分图的情况下,一个连通图最多可以被分成的组的个数即为图的直径(图中两个节点之间最远的距离),其实想到了之后验证起来就会觉得这也是一个很显然的事情(会的不难,难的不会,验证想法的难度总小于想到想法本身),只考虑直径这条路径,则这条路径从任意一端开始,执行bfs,将一次bfs中同一层的所有节点都放在同一个组中,如此反复,最终到直径的另一端,一定可以得到一种有效的分组,而直径又是图中的两节点之间的最长距离,因此不可能有数量更多的分组了。无向图的直径的计算最简便直接的方法是对每个节点都执行bfs,找到离该节点最远的节点的距离,所有距离中的最大值即为该图的直径。
|
||||
|
||||
### 代码
|
||||
```cpp
|
||||
class Solution {
|
||||
public:
|
||||
int bfs(int start, vector<vector<int>>& adj, int n) {
|
||||
vector<int> levels(n + 1, -1);
|
||||
queue<int> q;
|
||||
q.push(start);
|
||||
levels[start] = 0;
|
||||
int maxLevel = 0;
|
||||
|
||||
while (!q.empty()) {
|
||||
int curr = q.front();
|
||||
q.pop();
|
||||
|
||||
for (int next : adj[curr]) {
|
||||
if (levels[next] == -1) {
|
||||
levels[next] = levels[curr] + 1;
|
||||
maxLevel = max(maxLevel, levels[next]);
|
||||
q.push(next);
|
||||
}
|
||||
}
|
||||
}
|
||||
return maxLevel + 1; // 返回最大可能的分组数
|
||||
}
|
||||
|
||||
bool isBipartite(int start, vector<vector<int>>& adj, vector<int>& color, int n) {
|
||||
queue<int> q;
|
||||
q.push(start);
|
||||
color[start] = 0;
|
||||
|
||||
while (!q.empty()) {
|
||||
int curr = q.front();
|
||||
q.pop();
|
||||
|
||||
for (int next : adj[curr]) {
|
||||
if (color[next] == -1) {
|
||||
color[next] = 1 - color[curr];
|
||||
q.push(next);
|
||||
} else if (color[next] == color[curr]) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void dfs(int node, vector<vector<int>>& adj, vector<bool>& visited, vector<int>& component) {
|
||||
visited[node] = true;
|
||||
component.push_back(node);
|
||||
|
||||
for (int next : adj[node]) {
|
||||
if (!visited[next]) {
|
||||
dfs(next, adj, visited, component);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int magnificentSets(int n, vector<vector<int>>& edges) {
|
||||
vector<vector<int>> adj(n + 1);
|
||||
for (const auto& edge : edges) {
|
||||
adj[edge[0]].push_back(edge[1]);
|
||||
adj[edge[1]].push_back(edge[0]);
|
||||
}
|
||||
|
||||
vector<bool> visited(n + 1, false);
|
||||
vector<vector<int>> components;
|
||||
|
||||
for (int i = 1; i <= n; i++) {
|
||||
if (!visited[i]) {
|
||||
vector<int> component;
|
||||
dfs(i, adj, visited, component);
|
||||
components.push_back(component);
|
||||
}
|
||||
}
|
||||
|
||||
int result = 0;
|
||||
for (const auto& component : components) {
|
||||
vector<int> color(n + 1, -1);
|
||||
if (!isBipartite(component[0], adj, color, n)) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
// 对于每个连通分量,尝试从每个节点开始BFS,取最大值
|
||||
int maxGroups = 0;
|
||||
for (int node : component) {
|
||||
maxGroups = max(maxGroups, bfs(node, adj, n));
|
||||
}
|
||||
result += maxGroups;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
};
|
||||
```
|
||||
|
Loading…
Reference in New Issue
Block a user