社区讨论
圆方树做法另一疑问
P10779BZOJ4316 小 C 的独立集参与者 1已保存回复 0
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 0 条
- 当前快照
- 1 份
- 快照标识符
- @mhj2va27
- 此快照首次捕获于
- 2025/11/03 19:49 4 个月前
- 此快照最后确认于
- 2025/11/03 19:49 4 个月前
CPP
#include <algorithm>
#include <cstdio>
#include <cassert>
using namespace std;
typedef long long ll;
const int maxn = 5e4 + 5, maxm = 6e4 + 5, inf = 0x3f3f3f3f;
struct Edge {
int to, next;
} edge[maxm << 1];
int head[maxn], len;
void insert(const int &u, const int &v) {
edge[++len] = {v, head[u]}, head[u] = len;
}
int dfn[maxn], low[maxn], fa[maxn], Tim, f[maxn][2], n, m;
void DP(const int &u, const int &v) {
int g0, g1, f0 = 0, f1 = 0;
//
for (int x = v; x != u; x = fa[x]) {
g0 = f0 + f[x][0], g1 = f1 + f[x][1];
f0 = max(g0, g1), f1 = g0;
}
//
f[u][0] += f0;
f0 = 0, f1 = -inf;
for (int x = v; x != u; x = fa[x]) {
g0 = f0 + f[x][0], g1 = f1 + f[x][1];
f0 = max(g0, g1), f1 = g0;
}
f[u][1] += f1;
}
void Tarjan(const int &u) {
dfn[u] = low[u] = ++Tim, f[u][1] = 1;
for (int i = head[u], v; i; i = edge[i].next) {
if ((v = edge[i].to) == fa[u]) continue;
if (!dfn[v = edge[i].to]) fa[v] = u, Tarjan(v), low[u] = min(low[u], low[v]);
else low[u] = min(low[u], dfn[v]);
if (low[v] > dfn[u]) f[u][0] += max(f[v][0], f[v][1]), f[u][1] += f[v][0];
}
for (int i = head[u], v; i; i = edge[i].next) {
v = edge[i].to;
if (fa[v] != u && dfn[v] > dfn[u])
DP(u, v);
}
}
int main() {
scanf("%d%d", &n, &m);
for (int u, v; m; --m) scanf("%d%d", &u, &v), insert(u, v), insert(v, u);
Tarjan(1), printf("%d", max(f[1][0], f[1][1]));
return 0;
}
请问能否简要解释一下这个(位于两个行注释间的)转移究竟是什么意思?十分感谢。
回复
共 0 条回复,欢迎继续交流。
正在加载回复...