题意:一个公司有一个网络,连接着从编号1到N共N个地方,然后给出一些边,表示哪两个地方相连。有些点一旦断开所有和它关联的边,那么图不再联通,称这样的点为“critical place”,求有多少个这样的点。
分析:直接用dfs求割点数量就好了。
代码:
var e,t,s,n:longint; side:array[1..20000] of record x,y,next:longint; end; v:array[1..100] of boolean; last,low,dfn:array[1..100] of longint; procedure add(x,y:longint); begin inc(e); side[e].x:=x; side[e].y:=y; side[e].next:=last[x]; last[x]:=e; inc(e); side[e].x:=y; side[e].y:=x; side[e].next:=last[y]; last[y]:=e; end; procedure init; var x,y:longint; begin e:=0; fillchar(last,sizeof(last),0); read(x); while x>0 do begin while not eoln do begin read(y); add(x,y); end; readln; read(x); end; end; function min(x,y:longint):longint; begin if x<y then exit(x) else exit(y); end; procedure dfs(x:longint); var i:longint; begin inc(t); dfn[x]:=t; low[x]:=t; i:=last[x]; while i>0 do with side[i] do begin if dfn[y]=0 then begin if x=1 then inc(s); dfs(y); low[x]:=min(low[x],low[y]); if low[y]>=dfn[x] then v[x]:=true; end else low[x]:=min(low[x],dfn[y]); i:=next; end; end; procedure print; var ans,i:longint; begin ans:=0; if s>1 then v[1]:=true else v[1]:=false; for i:=1 to n do if v[i] then inc(ans); writeln(ans); end; procedure main; begin fillchar(low,sizeof(low),0); fillchar(dfn,sizeof(dfn),0); fillchar(v,sizeof(v),false); s:=0; t:=0; dfs(1); end; begin readln(n); while n>0 do begin init; main; print; readln(n); end; end.