BZOJ1123 BLO(tarjan割点)

来源:互联网 发布:写蒙古语软件下载 编辑:程序博客网 时间:2024/06/06 02:41

题目链接:BZOJ 1123
题目大意:一张无向图中,对于每一个点,求删去这个点后有多少对点不能相互到达。
题解:tarjan求割点。求出删除一个点后形成的几个联通块,任意不同联通块里的点不能互相到达。

代码(有参考hzwer大神(*^__^*) )

#include<iostream>#include<cstdio>#include<cstring>#include<cmath>#include<algorithm>using namespace std;int n,m,tot=0,ind;int head[100005],siz[100005],dfn[100005],low[100005];long long ans[100005];struct edge{    int to,ne;}e[1000005];void push(int x,int y){    e[++tot].to=y; e[tot].ne=head[x]; head[x]=tot;    e[++tot].to=x; e[tot].ne=head[y]; head[y]=tot;}void tarjan(int now){    int t=0;    siz[now]=1;    dfn[now]=low[now]=++ind;    for (int i=head[now];i;i=e[i].ne)    {        int v=e[i].to;        if (dfn[v]) low[now]=min(low[now],dfn[v]);         else          {              tarjan(v);              siz[now]+=siz[v];              low[now]=min(low[now],low[v]);              if (dfn[now]<=low[v])                {                  ans[now]+=(long long)t*siz[v];                  t+=siz[v];              }          }    }    ans[now]+=(long long)t*(n-t-1)}int main(){    scanf("%d%d",&n,&m);    for (int i=1;i<=m;i++)    {        int x,y;        scanf("%d%d",&x,&y);        push(x,y);    }    tarjan(1);    for (int i=1;i<=n;i++)     printf("%lld\n",(ans[i]+n-1)*2);}
原创粉丝点击