这个就是很裸的求割点的个数
关于割点什么的可以参考:http://blog.csdn.net/idrandom/article/details/52173817
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int Max=10050;
struct node{
int v,nxt;
int bri;//是否是桥
}e1[Max];
int h[Max];
int dfn[Max],low[Max],mst[Max],vis[Max];
int cut[Max],ad[Max];
int siz,idx,st,ct,br;
void init(){
memset(e1,-1,sizeof e1);
memset(h,-1,sizeof h);
memset(vis,0,sizeof vis);
memset(ad,0,sizeof ad);
memset(cut,0,sizeof cut);
siz=idx=st=ct=br=0;
}
void add(int u,int v){
e1[siz].nxt=h[u];
e1[siz].v=v;
e1[siz].bri=0;
h[u]=siz++;
}
void tarjan(int u,int fa){
int v;
low[u]=dfn[u]=++idx;
mst[++st]=u;
vis[u]++;
int son=0;
for(int i=h[u];~i;i=e1[i].nxt){
v=e1[i].v;
if(v==fa)continue;
if(!vis[v]){
son++;
tarjan(v,u);
if(low[u]>low[v])low[u]=low[v];
//桥
if(low[v]>dfn[u]){
++br;
e1[i].bri=1;
e1[i^1].bri=1;
}
//割点
if(fa&&low[v]>=dfn[u]){//不是根
cut[u]=1;
ad[u]++;
}
}
else if(dfn[v]<low[u])low[u]=dfn[v];
}
if((!fa)&&son>1)cut[u]=1;
if(!fa)ad[u]=son-1;
vis[u]++;
st--;
}
char str[505];
int main(){
int n;
while(~scanf("%d",&n)&&n){
init();
getchar();
while(gets(str)){
if(str[0]=='0')break;
int len=strlen(str);
int u=0,v=0;
for(int i=0;i<len;i++){
if(!u){
while(i<len&&str[i]!=' '){u*=10;u+=(str[i++]-'0');}
i++;
}
while(i<len&&str[i]!=' '){v*=10;v+=(str[i]-'0');i++;}
add(u,v);
add(v,u);
v=0;
}
}
for(int i=1;i<=n;i++){
if(!vis[i])tarjan(i,0);
}
int ans=0;
for(int i=1;i<=n;i++){
if(cut[i])ans++;
}
printf("%d\n",ans);
}
return 0;
}
刚开始输入写挂了居然出了样例。。。蜜汁wa