给一个网络, 需要求出割点和被这个割点割成的子网络的个数 #include<stdio.h> #include<string.h> const int MAXN = 1001; int low[MAXN], dfn[MAXN], ans[MAXN], map[MAXN][MAXN]; int n, cnt; void dfs(int now){ dfn[now] = low[now] = cnt++; for(int i = 1; i <= n; ++i){ if(map[now][i]){ if(dfn[i] == 0){ //forward edge dfs(i); //继续递归 if(low[now] > low[i]) low[now] = low[i]; if(dfn[now] <= low[i]) ans[now]++; //直接累加 } else { //back edge if(low[now] > dfn[i]) low[now] = dfn[i]; } } } } void init(){ memset(ans, 0, sizeof(ans)); memset(map, 0, sizeof(map)); memset(dfn, 0, sizeof(dfn)); memset(low, 0, sizeof(low)); cnt = 1; } void solve(){ bool ok = true; dfs(1); //1为根 ans[1]--; //为根时要减一,因为为根时有大于等于两个子树时才是割点 for(int i = 1; i <= n; ++i){ if(ans[i] > 0){ printf(" SPF node %d leaves %d subnets/n",i, ans[i] + 1); ok = false; } } if(ok){ printf(" No SPF nodes/n"); } printf("/n"); } int main(){ int a, b, cases = 0; while(scanf("%d",&a), a){ init(); n = 0; scanf("%d",&b); //printf("a , b =%d%d/n",a, b); map[a][b] = map[b][a] = 1; n = a > b ? a : b; while(scanf("%d",&a), a){ scanf("%d",&b); // printf("a , b =%d%d/n",a, b); map[a][b] = map[b][a] = 1; n = n > (a > b ? a : b) ? n : (a > b ? a : b); } printf("Network #%d/n",++cases); solve(); } return 0; }