题意:给出一个网络(不一定连通),求所有的割点,以及割点可以切分出多少个连通分量。

思路:很多种情况。

(1)如果给的图已经不是连通图,直接“  No SPF nodes”。

(2)求所有割点应该不难,就是tarjan发明的算法搞定。但是求连通分量就得小心了,多种情况。看下:

  1)如果一个割点x,其所有孩子都不是割点,那么x至少可以割出两个连通分量(x之上和之下的各1个)。

  2)如果一个割点x,其有部分孩子是割点,有部分孩子并不是割点,那么x可以割出x之上的1个连通分量,不是割点的孩子均是同1个连通分量,是割点的孩子各自分别是一个连通分量。

  3)如果一个割点x,如果有些孩子是叶子节点,且该叶子节点的度为1,即连着x,那么该叶子节点会被割出来,单点也是连通分量。

 //#include <bits/stdc++.h>
#include <iostream>
#include <cmath>
#include <cstdio>
#include <vector>
#include <cstring>
#include <climits>
using namespace std;
const int N=;
int mapp[N][N];
int cntr, flag, up; //时间戳
int dfn[N], low[N], vis[N], iscut[N], cur[N]; //记录时间戳, 反边最顶点, 访问记录, 是否连通分量 bool DFS(int x, int far)
{
int chd=; //孩子节点个数
int cnt=, sum=;
dfn[x]=low[x]=++cntr; //时间戳
vis[x]=; //DFS必备
for(int i=; i<=up; i++)
{
if(!mapp[i][x]) continue;
if(!vis[i]) //树边
{
chd++;
bool f=DFS(i,x); //i点只有一条边
low[x]=min(low[x],low[i]); //判断连通分量的个数
if(!far && chd> || far && low[i]>=dfn[x] ) //能让x成为割点的孩子i
{ sum++;
iscut[x]=;
if(iscut[i]||f) cnt++; //这个孩子是割点或者满足单点单边条件
}
}
else if(i!=far)
low[x]=min(low[x], dfn[i]);
}
if(!far && iscut[x])
{
iscut[x]=cnt; //根节点
if(sum>cnt) iscut[x]++;
}
if( far && iscut[x]) //非根节点
{
if(!cnt ) iscut[x]=; //没有“是割点”的孩子,那么只要自己是割点,起码可以割为两个连通分量
else if(sum==cnt) iscut[x]=cnt+; //有“是割点”的孩子,那么每个“割点”孩子是1个连通分量,注:有可能还有非割点孩,他们算1个连通分量
else iscut[x]=cnt+;
}
if(iscut[x]) flag=; //无割点的标记'
//if(x==1) cout<<"**"<<sum<<endl; if(!chd && low[x]==dfn[x] ) return true; //返回值用于判断是否是叶子,且没有反向边到fa之上
return false;
} void cal() //n为边数
{ flag=cntr=;
DFS(up,); //深搜求割点数
int i;
for(i=; i<=up; i++) //先确保是个连通图
if(cur[i]&&!vis[i])
{
printf(" No SPF nodes\n");
return ;
} for(i=; i<=up; i++)
if(cur[i]&&iscut[i])
{
printf(" SPF node %d leaves %d subnets\n", i, iscut[i]);
} if(!flag) printf(" No SPF nodes\n");
}
void init()
{
up=;
memset(cur,,sizeof(cur));
memset(mapp,,sizeof(mapp));
memset(vis,,sizeof(vis));
memset(dfn,,sizeof(dfn));
memset(low,,sizeof(low));
memset(iscut,,sizeof(iscut)); } int main()
{
freopen("input.txt", "r", stdin);
int j=, a, b;
while()
{
int cnt=;
init();
while(~scanf("%d",&a))
{
if(!a && !cnt) return ; //没边,a又为0,则结束了
if(!a)
{
printf("Network #%d\n",++j);
cal();
printf("\n");break;
}
scanf("%d",&b);
up=max(max(up,a),b); //记录顶点号上限
cur[a]=cur[b]=; //记录出现的顶点号
mapp[a][b]=mapp[b][a]=; //矩阵
cnt++; //边数
}
}
return ;
}

AC代码

POJ 1523 SPF (割点,连通分量)的更多相关文章

  1. poj 1523 SPF(双连通分量割点模板)

    题目链接:http://poj.org/problem?id=1523 题意:给出无向图的若干条边,求割点以及各个删掉其中一个割点后将图分为几块. 题目分析:割点用tarjan算法求出来,对于每个割点 ...

  2. POJ 1523 SPF 割点 Tarjan

    SPF Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 9317   Accepted: 4218 Description C ...

  3. POJ 1523 SPF 割点与桥的推断算法-Tarjan

    题目链接: POJ1523 题意: 问一个连通的网络中有多少个关节点,这些关节点分别能把网络分成几部分 题解: Tarjan 算法模板题 顺序遍历整个图,能够得到一棵生成树: 树边:可理解为在DFS过 ...

  4. Electricity POJ - 2117 + SPF POJ - 1523 去除割点后求强连通分量个数问题

    Electricity POJ - 2117 题目描述 Blackouts and Dark Nights (also known as ACM++) is a company that provid ...

  5. zoj 1119 / poj 1523 SPF (典型例题 求割点 Tarjan 算法)

    poj : http://poj.org/problem?id=1523 如果无向图中一个点 u 为割点 则u 或者是具有两个及以上子女的深度优先生成树的根,或者虽然不是一个根,但是它有一个子女 w, ...

  6. POJ 1523 SPF tarjan求割点

                                                                   SPF Time Limit: 1000MS   Memory Limit ...

  7. POJ 1523 SPF(求割点)

    题目链接 题意 : 找出图中所有的割点,然后输出删掉他们之后还剩多少个连通分量. 思路 : v与u邻接,要么v是u的孩子,要么u是v的祖先,(u,v)构成一条回边. //poj1523 #includ ...

  8. POJ 1523 SPF (无向图割点)

    <题目链接> 题目大意: 给你一个连通的无向图,问你其中割点的编号,并且输出删除该割点后,原图会被分成几个连通分量. 解题分析: Tarjan求割点模板题. #include <cs ...

  9. poj 1523 SPF(tarjan求割点)

    本文出自   http://blog.csdn.net/shuangde800 ------------------------------------------------------------ ...

随机推荐

  1. HDU 1423 Greatest Common Increasing Subsequence LCIS

    题目链接: 题目 Greatest Common Increasing Subsequence Time Limit: 2000/1000 MS (Java/Others) Memory Limit: ...

  2. [nowCoder] 两个不等长数组求第K大数

    给定两个有序数组arr1和arr2,在给定一个整数k,返回两个数组的所有数中第K小的数.例如:arr1 = {1,2,3,4,5};arr2 = {3,4,5};K = 1;因为1为所有数中最小的,所 ...

  3. Linux下配置安装PHP环境

    参考别人的做法,遇到问题上网查,下面就是安装步骤. 一.安装Apache2.2.221.到官网下载  http://httpd.apache.org/download.cgi    2.解压    t ...

  4. 浏览器后退按钮导致jquery动态添加的select option值丢失的解决方法

    监控浏览器返回功能 判断浏览器返回功能 禁用浏览器的后退按钮 JS禁止浏览器后退键 http://volunteer521.iteye.com/blog/830522/ 浏览器返回功能 判断上一页面来 ...

  5. Installing Lua in Mac

    Lua is distributed in source form. You need to build it before using it. Building Lua should be stra ...

  6. 【好玩的应用】QQ连连看辅助工具

    自己学了这么久的C语言,但没有写出过什么可以用的东西来,总觉得心里不爽.这几天实在是不想干正事,在网上瞎逛逛,结果发现有人写了连连看的外挂.顿时觉得这很有意思啊.于是把代码下载下来,捣鼓了捣鼓.发现还 ...

  7. poj 3270 Cow Sorting

    思路:仔细读题,看到FARMER是两两交换牛的顺序进行排序的话,应该就往置换上靠拢,而这个题果然是置换的应用(有的解题报告上说是置换群,其实这只是单个置换,不用让它构成群).我们来将这些无序的牛抽象成 ...

  8. hdu 1333 Smith Numbers

    刚开始没看清题意,要找的数一定要是素数 ;}

  9. [SQL Server系] -- 视图

    1:定义 从用户角度来看,一个视图是从一个特定的角度来查看数据库中的数据. 从数据库系统内部来看,一个视图是由SELECT语句组成的查询定义的虚拟表. 从数据库系统内部来看,视图是由一张或多张表中的数 ...

  10. struts2配置文件中action的name属性

    struts2配置文件中action的name属性的第一个字符不要加斜杠 <action name="see" class="baoxiuManage_seeAct ...