POJ 2942(Tarjen的点双连通分量+交叉染色法)
来源:互联网 发布:怎么免费装修淘宝店铺 编辑:程序博客网 时间:2024/06/05 04:54
这题是点双连通分量,我一开始写成边的……
首先点双连通分量可能重叠……(1,2) (2,3) (3,1) (3,4) (4,5) (5,6) (3.6)
这时有(1,2,3)和(3,4,5,6)两组双连通分量
故一定要在Tarjen里判……另外Stack存边时注意特判(Stack不能为空)
当dfs[k]<=low[i] 时 就找到了点双连通分量 (这是点双连通)
请注意在推送(k,i)后遍历得到的一堆边(包括(k,i))组成了一组点双连通分量
两个重要定理:
(1) 如果一个双连通分量内的某些顶点在一个奇圈中(即双连通分量含有奇圈),那么这个双连通分量的其他顶点也在某个奇圈中;
(2) 如果一个双连通分量含有奇圈,则他必定不是一个二分图。反过来也成立,这是一个充要条件。
Program P2942;const maxn=1050; maxm=1000000;Var n,m,i,j,x,y:longint; b:array[1..maxn,1..maxn] of boolean; color,c,dfs,low:array[1..maxn] of longint; attend,flag:array[1..maxn] of boolean; size,time,totssc:longint; stack:array[0..maxm,1..2] of longint;function min(a,b:longint):longint;begin if a<b then exit(a) else exit(b);end;function is_Binary(k,col:longint):boolean;var i,j:longint;begin color[k]:=col; for i:=1 to n do if (flag[i]) and (b[k,i]) then begin if color[i]=0 then begin if not(is_binary(i,3-col)) then exit(false); end else if color[k]=color[i] then exit(false); end; exit(true);end;procedure tarjen(k,father:longint);var i,j:longint;begin inc(time); dfs[k]:=time; low[k]:=time; c[k]:=1; for i:=1 to n do if (b[k,i]) and (dfs[k]>dfs[i]) and (i<>father) then begin if dfs[i]=0 then begin inc(size); stack[size,1]:=k; stack[size,2]:=i; tarjen(i,k); low[k]:=min(low[k],low[i]); if dfs[k]<=low[i] then begin fillchar(flag,sizeof(flag),false); fillchar(color,sizeof(color),false); while (size>0) do begin flag[stack[size,1]]:=true; flag[stack[size,2]]:=true; dec(size); if (stack[size+1,1]=k) and (stack[size+1,2]=i) then break; end; if not(is_binary(k,1)) then begin for j:=1 to n do if flag[j] then attend[j]:=true; end; end; end else if c[i]=1 then low[k]:=min(low[k],dfs[i]); end; c[k]:=2;end;function main:longint;var i,j,tot:longint;begin fillchar(dfs,sizeof(dfs),0); fillchar(low,sizeof(low),0); fillchar(c,sizeof(c),0); fillchar(attend,sizeof(attend),false); fillchar(flag,sizeof(flag),false); fillchar(color,sizeof(color),0); fillchar(stack,sizeof(stack),0); size:=0;time:=0; for i:=1 to n do if (dfs[i]=0) then begin tarjen(i,0); end; tot:=0; for i:=1 to n do if attend[i] then inc(tot); exit(n-tot);end;begin while not seekeof do begin read(n,m); if (n=0) and (m=0) then break; fillchar(b,sizeof(b),true); for i:=1 to n do b[i,i]:=false; for i:=1 to m do begin read(x,y); b[x,y]:=false; b[y,x]:=false; end; writeln(main); end;end.
- POJ 2942(Tarjen的点双连通分量+交叉染色法)
- poj 2942(奇圈,双连通分量,交叉染色)
- poj 2942 Knights of the Round Table 点双连通分量+交叉染色法
- POJ 2942 Knights of the Round Table (点-双连通分量 + 交叉法染色判二分图)
- poj 2942 点双连通分量+二分图染色
- POJ 2942 点的双连通分量
- poj 2942 双连通分量+二分图的染色判断
- poj2942[补图+点双连通分量+交叉染色法判定二分图(奇圈判定)]
- POJ 2942—— Knights of the Round Table双连通分量+交叉染色
- POJ 2942 Knights of the Round Table [二分图染色][点双连通分量]
- [POJ]2942 圆桌骑士 点双连通分量 + 二分图染色
- poj 2942 双连通分量+染色判二部图(驱除骑士)
- POJ 2942 双连通分量
- POJ 1523 SPF (割顶 点双连通分量)
- POJ 1523SPF 点双连通分量
- poj 3177 双连通分量+缩点
- Knights of the Round Table-POJ2942(双连通分量+交叉染色)
- 点双连通分量
- 判断一个自然数是否是某个数的平方
- Android自动化测试手段之Monkey(adb shell monkey)
- 多台笔记本同时上网方法
- js 调用不同的js函数列表的时候, 中间需要时间间隔
- ifconfig 与永久修改MAC地址
- POJ 2942(Tarjen的点双连通分量+交叉染色法)
- ClientdataSet 三层中主从表的操作
- 关于rsync
- SWFUpload详解 java后台接收实例(包括传参问题)
- windbg 调试 win7
- C语言中static的作用
- gdb中常用的一些命令
- 两分钟彻底让你明白Android Activity生命周期
- 程序员编程技术迅速提高的终极攻略