bzoj2730 & world final 2011 H

1、题目大意:就是有一个无向图,让你在里面选择点,使得,无论哪个点没了以后,其他的点都能到达你选择的任何一个点,输出最少
选择几个点,和选择最少的方案数,最多有500条边。

2、分析:首先我们想如果没得不是割顶,那么其他的都无所谓了。

然后如果没有割顶,那就是选两个点,(避免其中你选的点没了)

如果有,我们把所有的割顶去掉,得到一些连通分量,那么如果一个连通分量里连着不止一个割顶,这个连通分量就可以去别 的连通分量里,如果只连着一个割顶,那么这个联通分量里就要选一个点了,选哪个点无所谓,因为是双联通分量啊,我不是

把割顶都去掉了吗,最后乘法原理什么的,搞一搞就过了,交了那么多次,居然是因为最后输出没用 long long,浪费我的提交
次数,加一个优化,如果一个连通分量已经dfs到它连着超过1个更定了,就结束dfs

#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
using namespace std;
#define LL long long
LL head[100100], next[100100];
LL u[100100], v[100100];
LL pre[100010];
bool iscut[100010];
LL cnt1;
bool vis[100010];
LL dfs_clock;
LL block[100010];
LL cnt2;
LL kk[100010], tot;
bool vis_block[100010];
LL dfs(LL x, LL fa){
    LL lowx = pre[x] = ++ dfs_clock;
    LL cnt = 0;
    for(LL i = head[x]; i != -1; i = next[i]){
        LL y = v[i];
        if(!pre[y]){
            cnt ++;
            LL lowy = dfs(y, x);
            lowx = min(lowx, lowy);
            if(lowy >= pre[x]) iscut[x] = true;
        }
        else if(pre[y] < pre[x] && y != fa){
            lowx = min(lowx, pre[y]);
        }
    }
    if(cnt == 1 && fa < 0) iscut[x] = false;
    return lowx;
}
void solve(LL x, LL fa){
    vis[x] = 1;
    block[x] = cnt1;
    for(LL i = head[x]; i != -1; i = next[i]){
        LL y = v[i];
        if(!vis[y]){
            solve(y, x);
        }
    }
}

void get_ans(LL x, LL fa){
    vis[x] = 1;
    cnt2 ++;
    if(cnt1 > 1) return;
    for(LL i = head[x]; i != -1; i = next[i]){
        LL y = v[i];
        if(cnt1 > 1) return;
        if(!vis[y]){
            if(iscut[y]){
                vis[y] = true;
                kk[++ tot] = y;
                cnt1 ++;
                continue;
            }
            get_ans(y, x);
        }
    }
}
int main(){
    LL n;
    LL h = 0;
    while(scanf("%lld", &n) != EOF){
        if(n == 0) return 0;
        h ++;
        memset(head, -1, sizeof(head));
        LL m = 0;
        for(LL i = 1; i <= n; i ++){
            scanf("%lld%lld", &u[2 * i - 1], &v[2 * i - 1]);
            m = max(m, u[2 * i - 1]);
            m = max(m, v[2 * i - 1]);
            u[2 * i] = v[2 * i - 1];
            v[2 * i] = u[2 * i - 1];
            next[2 * i - 1] = head[u[2 * i - 1]];
            head[u[2 * i - 1]] = 2 * i - 1;
            next[2 * i] = head[u[2 * i]];
            head[u[2 * i]] = 2 * i;
        }
        dfs_clock = 0;
        memset(iscut, 0, sizeof(iscut));
        memset(pre, 0, sizeof(pre));
        LL wl = dfs(1, -1);
        for(LL i = 1; i <= m; i ++) vis[i] = iscut[i];
        for(LL i = 1; i <= m; i ++){
            if(!vis[i]){
                cnt1 ++;
                solve(i, -1);
            }
        }
        memset(vis, 0, sizeof(vis));
        LL ans1 = 0, ans2 = 1;
        tot = 0;
        memset(vis_block, 0, sizeof(vis_block));
        for(LL i = 1; i <= m; i ++){
            if(!iscut[i] && !vis[i] && !vis_block[block[i]]){
                cnt1 = 0;
                cnt2 = 0;
                get_ans(i, -1);
                if(cnt1 == 1){
                    ans1 ++;
                    ans2 *= cnt2;
                }
                for(LL j = 1; j <= tot; j ++){
                    vis[kk[j]] = 0;
                }
                tot = 0;
                vis_block[block[i]] = 1;
            }
        }
        if(ans1 == 0) printf("Case %lld: 2 %lld\n", h, m * (m - 1) / 2);
        else printf("Case %lld: %lld %lld\n", h, ans1, ans2);
    }
    return 0;
}

BZOJ2730——[HNOI2012]矿场搭建的更多相关文章

  1. bzoj2730 [HNOI2012]矿场搭建 (UVAlive5135 Mining Your Own Business)

    2730: [HNOI2012]矿场搭建 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1147  Solved: 528[Submit][Statu ...

  2. [BZOJ2730][HNOI2012]矿场搭建 点双 割点

    2730: [HNOI2012]矿场搭建 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 2852  Solved: 1344[Submit][Stat ...

  3. BZOJ2730 [HNOI2012]矿场搭建 - Tarjan割点

    Solution 输入中没有出现过的矿场点是不用考虑的, 所以不用考虑只有 一个点 的点双联通分量. 要使某个挖矿点倒塌, 相当于割去这个点, 所以我们求一遍割点和点双联通分量. 之后的点双联通分量构 ...

  4. BZOJ2730: [HNOI2012]矿场搭建

    传送门 图的连通性相关的必和割点割边之类的有关. 题目要求对于一个无向图,任意一点被删除后,所有点都和某些指定点是联通的. 这道题比较简单的做法就是求出来所有的块.对于一个块,如果块里有两个及两个以上 ...

  5. [BZOJ2730][HNOI2012]矿场搭建(求割点)

    题目:http://www.lydsy.com:808/JudgeOnline/problem.php?id=2730 分析: 如果坍塌的点不是割点,那没什么影响,主要考虑坍塌的点是割点的情况. 显然 ...

  6. 【双连通分量】Bzoj2730 HNOI2012 矿场搭建

    Description 煤矿工地可以看成是由隧道连接挖煤点组成的无向图.为安全起见,希望在工地发生事故时所有挖煤点的工人都能有一条出路逃到救援出口处.于是矿主决定在某些挖煤点设立救援出口,使得无论哪一 ...

  7. BZOJ2730:[HNOI2012]矿场搭建(双连通分量)

    Description 煤矿工地可以看成是由隧道连接挖煤点组成的无向图.为安全起见,希望在工地发生事故时所有挖煤点的工人都能有一条出路逃到救援出口处.于是矿主决定在某些挖煤点设立救援出口,使得无论哪一 ...

  8. BZOJ2730 [HNOI2012]矿场搭建[点双连通分量]

    看到删去一个点,需要剩下的都和关键点连通,有端联想到找点双,因为他怎么删点都是连通的. 对于一个孤立的点双,至少要设两个关键点. 如果两个点双以一个割点连接,假设断掉这个割点,两个块至少要各设一个关键 ...

  9. [BZOJ2730]:[HNOI2012]矿场搭建(塔尖)

    题目传送门 题目描述 煤矿工地可以看成是由隧道连接挖煤点组成的无向图.为安全起见,希望在工地发生事故时所有挖煤点的工人都能有一条出路逃到救援出口处.于是矿主决定在某些挖煤点设立救援出口,使得无论哪一个 ...

随机推荐

  1. HTML中<meta>标签如何正确使用

    HTML中<meta>标签如何正确使用 如果我们在浏览器中按下F12或者Ctrl+shift+J,便可以打开开发者工具,在element中即可看到<head>元素中有不少< ...

  2. paramiko模块使用

    paramiko是一个用于做远程控制的模块,使用该模块可以对远程服务器进行命令或文件操作,fabric和ansible内部远程管理就是使用paramiko来实现. #!/usr/bin/env pyt ...

  3. iterator and iterable

    前者是迭代器 后者是接口,List等继承这个接口

  4. Sublime Text3快捷键汇总

    选择类 Ctrl+D 选中光标所占的文本,继续操作则会选中下一个相同的文本. Alt+F3 选中文本按下快捷键,即可一次性选择全部的相同文本进行同时编辑.举个栗子:快速选中并更改所有相同的变量名.函数 ...

  5. windows 修改hosts 脚本

    @echo off echo "请注意你的杀毒软件提示,一定要允许" echo. & pause @del C:\Windows\System32\drivers\etc\ ...

  6. asp+mysql__不同类型用户登录

    未防注入//0.0 /***这里代码应用场景为多类用户登录,根据用户选择不同的单选按钮判断用户登录的类型,*从而进行不同的数据表进行判断,用户的用户名和密码是否正确.*/ public partial ...

  7. CentOS_PHP_NGINX_FastCGI

    yum安装nginx,它会默认作为一个服务加到系统中,启动nginx: service nginx start/nginx -s start 他有4个参数(start|stop|restart|rel ...

  8. GoLang之网络

    GoLang之网络 Go语言标准库里提供的net包,支持基于IP层.TCP/UDP层及更高层面(如HTTP.FTP.SMTP)的网络操作,其中用于IP层的称为Raw Socket. net包的Dial ...

  9. Python开发【第十二篇】:DOM

    文档对象模型(Document Object Model,DOM)是一种用于HTML和XML文档的编程接口.它给文档提供了一种结构化的表示方法,可以改变文档的内容和呈现方式.我们最为关心的是,DOM把 ...

  10. 用java实现zip压缩

    本来是写到spaces live上的,可是代码的显示效果确实不怎么好看.在javaeye上试了试代码显示的顺眼多了. 今天写了个用java压缩的功能,可以实现对文件和目录的压缩. 由于java.uti ...