题目:http://acm.hdu.edu.cn/showproblem.php?pid=5934

  1. 根据距离关系建边
  2. 对于强连通分量来说,只需引爆话费最小的炸弹即可引爆整个强连通分量
  3. 将所有的强连通分量缩成点,我们就得到了一棵树,我们只需要引爆树根的炸弹即可
  4. 我们可以处理出每个点所属的强连通分量的拓扑序,或者说染色法,把属于同一个强连通分量的点标上同一个数字
  5. 处理完强连通分量后,我们不需要建树,我们可以用并查集来维护,更好的办法是统计每个点的入度,入读为0即为根节点
     #include<bits/stdc++.h>
    using namespace std;
    typedef long long ll;
    const int maxv = ;
    int V;//总共点的个数
    vector<int> g[maxv];
    vector<int> rg[maxv];
    vector<int> vs;
    bool used[maxv];
    int cmp[maxv];//保存拓扑序
    ll cost[maxv];//每个拓扑序的话费
    ll x[],y[],r[],c[];
    ////scc
    void dfs(int v){
    used[v] = true;
    for(int i = ;i<g[v].size();i++)
    if(!used[g[v][i]])
    dfs(g[v][i]);
    vs.push_back(v);
    }
    void rdfs(int v,int k){
    used[v] = true;
    cmp[v] = k;
    cost[k] = min(cost[k],c[v]);//处理出每个强连通分量的最小话费
    for(int i = ;i<rg[v].size();i++)
    if(!used[rg[v][i]])
    rdfs(rg[v][i],k);
    }
    int scc(){
    memset(used,,sizeof(used));
    vs.clear();
    for(int v = ;v<=V;v++)//这里要注意,下标是从0开始还是从1开始
    if(!used[v])
    dfs(v);
    memset(used,,sizeof(used));
    int k = ;
    for(int i = vs.size()-;i>=;i--)
    if(!used[vs[i]])
    rdfs(vs[i],k++);
    return k;
    }
    //////
    void addedge(int i,int j){
    ll dis = (y[i]-y[j])*(y[i]-y[j])+(x[i]-x[j])*(x[i]-x[j]);
    if(dis <= r[i]*r[i]){
    g[i].push_back(j);
    rg[j].push_back(i);
    }
    if(dis <= r[j]*r[j]){
    g[j].push_back(i);
    rg[i].push_back(j);
    }
    }
    //////
    int du[];
    int main(){
    int t;
    cin >> t;
    int cas = ;
    while(t--){
    int n;
    cin >> n;
    V = n;
    memset(cost,0x3f3f3f3f,sizeof(cost));
    for(int i = ;i<=n;i++){
    g[i].clear();
    rg[i].clear();
    }
    for(int i = ;i<=n;i++){
    scanf("%I64d%I64d%I64d%I64d",&x[i],&y[i],&r[i],&c[i]);
    for(int j = ;j<i;j++){
    addedge(i,j);
    }
    }
    int k = scc();
    memset(du,,sizeof(du));
    for(int i = ;i<=n;i++)
    for(int j = ;j<g[i].size();j++)
    if(cmp[i] != cmp[g[i][j]])//拓扑序不同,度数加1
    du[cmp[g[i][j]]]++;
    ll ans = ;
    for(int i = ;i<k;i++)
    if(du[i] == )
    ans += cost[i] ;
    printf("Case #%d: %I64d\n",cas++,ans);
    }
    return ;
    }

HDU5934 强连通分量的更多相关文章

  1. 【HDU5934】Bomb——有向图强连通分量+重建图

    题目大意 二维平面上有 n 个爆炸桶,i−thi-thi−th爆炸桶位置为 (xi,yi)(x_i, y_i)(xi​,yi​) 爆炸范围为 rir_iri​ ,且需要 cic_ici​ 的价格引爆, ...

  2. POJ1236Network of Schools[强连通分量|缩点]

    Network of Schools Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 16571   Accepted: 65 ...

  3. 有向图的强连通分量的求解算法Tarjan

    Tarjan算法 Tarjan算法是基于dfs算法,每一个强连通分量为搜索树中的一颗子树.搜索时,把当前搜索树中的未处理的结点加入一个栈中,回溯时可以判断栈顶到栈中的结点是不是在同一个强连通分量中.当 ...

  4. Tarjan算法--强连通分量

    tarjan的过程就是dfs过程. 图一般能画成树,树的边有三种类型,树枝边 + 横叉边(两点没有父子关系) + 后向边(两点之间有父子关系): 可以看到只有后向边能构成环,即只有第三张图是强连通分量 ...

  5. 强连通分量的一二三 | | JZOJ【P1232】 | | 我也不知道我写的什么

    贴题: 在幻想乡,上白泽慧音是以知识渊博闻名的老师.春雪异变导致人间之里的很多道路都被大雪堵塞,使有的学生不能顺利地到达慧音所在的村庄.因此慧音决定换一个能够聚集最多人数的村庄作为新的教学地点.人间之 ...

  6. 有向图强连通分量的Tarjan算法

    有向图强连通分量的Tarjan算法 [有向图强连通分量] 在有向图G中,如果两个顶点间至少存在一条路径,称两个顶点强连通(strongly connected).如果有向图G的每两个顶点都强连通,称G ...

  7. poj2186Popular Cows(Kosaraju算法--有向图的强连通分量的分解)

    /* 题目大意:有N个cows, M个关系 a->b 表示 a认为b popular:如果还有b->c, 那么就会有a->c 问最终有多少个cows被其他所有cows认为是popul ...

  8. Tarjan应用:求割点/桥/缩点/强连通分量/双连通分量/LCA(最近公共祖先)【转】【修改】

    一.基本概念: 1.割点:若删掉某点后,原连通图分裂为多个子图,则称该点为割点. 2.割点集合:在一个无向连通图中,如果有一个顶点集合,删除这个顶点集合,以及这个集合中所有顶点相关联的边以后,原图变成 ...

  9. POJ 1236 Network of Schools(强连通分量/Tarjan缩点)

    传送门 Description A number of schools are connected to a computer network. Agreements have been develo ...

随机推荐

  1. [No00009B]win10快捷键大全

    微软为Win10命令行(Command Prompt)加入了Ctrl + V的支持 Win10新增功能快捷键大全: 贴靠窗口:Win + 左/右 >  Win + 上/下 > 窗口可以变为 ...

  2. jdbc java数据库连接 8)防止sql注入

    回顾下之前jdbc的开发步骤: 1:建项目,引入数据库驱动包 2:加载驱动 Class.forName(..); 3:获取连接对象 4:创建执行sql语句的stmt对象;  写sql 5:执行sql ...

  3. [译]RxJS 5.X基础篇

    欢迎指错与讨论 : ) 当前RxJS版本:5.0.0-beta.10.更详细的内容尽在RxJS官网http://reactivex.io/rxjs/manual/overview.html.文章比较长 ...

  4. C++ 使用ifstream读取数据,多读最后一行问题解决方法

    C++文件读取时有一个bug,就是使用eof()判断文件结尾并不准确,最后一行会重复读取一次,可采用以下方法避免重复读取: while (!inFile.eof()) { inFile >> ...

  5. [LeetCode] Split Array Largest Sum 分割数组的最大值

    Given an array which consists of non-negative integers and an integer m, you can split the array int ...

  6. [LeetCode] Shortest Word Distance II 最短单词距离之二

    This is a follow up of Shortest Word Distance. The only difference is now you are given the list of ...

  7. css一些进入条

    http://www.jq22.com/jquery-info5309 http://www.jq22.com/jquery-info10964 http://www.jq22.com/jquery- ...

  8. mysq大数据分页

    mysql limit大数据量分页优化方法 Mysql的优化是非常重要的.其他最常用也最需要优化的就是limit.Mysql的limit给分页带来了极大的方便,但数据量一大的时候,limit的性能就急 ...

  9. Android Hook技术

    原文:http://blog.csdn.net/u011068702/article/details/53208825 附:Android Hook 全面入侵监听器 第一步.先爆项目demo照片,代码 ...

  10. <form:select>的使用

    最近在学习springMVC,用到了<form:select>标签,使用发过程中遇到了些问题,现在记录下,以防忘记. 我jsp页面是这样的: <%@ page language=&q ...