【模板】tarjan割点
注意有两个变量
now是判断x是不是根,并不是父节点
#include<bits/stdc++.h> using namespace std; const int maxn = 100005; struct edge{ int to, next; }e[maxn << 1]; int head[maxn], cnt; int n, m, a, b; int low[maxn], dfn[maxn], ch, cut[maxn], ans, num; void add(int u, int v) { e[++cnt].to = v; e[cnt].next = head[u]; head[u] = cnt; } void tarjan(int x, int now) { dfn[x] = low[x] = ++num; ch = 0; for(int i = head[x]; i; i = e[i].next) { int y = e[i].to; if(!dfn[y]) { tarjan(y, x); low[x] = min(low[x], low[y]); if(low[y] >= dfn[x] && now != -1) cut[x] = 1; } else if(x != now) low[x] = min(low[x], dfn[y]); } if(now == -1 && ch > 1) cut[x] = 1; } int main() { cin >> n >> m; for(int i = 1; i <= m; i++) { scanf("%d%d", &a, &b); add(a, b); add(b, a); } for(int i = 1; i <= n; i++) if(!dfn[i]) tarjan(i, -1); for(int i = 1; i <= n; i++) if(cut[i]) ans++; printf("%d\n", ans); for(int i = 1; i <= n; i++) if(cut[i]) printf("%d ", i); return 0; }

浙公网安备 33010602011771号