题解见这个博客:http://blog.csdn.net/ME495/article/details/76165039

  复杂度不太会算。。这个经典问题的解法需要注意,维护队列里面只有k个元素即可。另外,tarjan对无向图仙人掌图缩点(即只把所有环变成一个点)得注意一下(栈得手写才能实现要求,这是因为在这里割边不能被算进环内,而在有向图中,一个点也算是强连通分量的)。

  代码如下:

 #include <stdio.h>
#include <algorithm>
#include <string.h>
#include <vector>
#include <stack>
#include <queue>
using namespace std;
const int N = + ;
typedef pair<int, int> pii; struct edge
{
int u, v, w;
};
int n, m, k;
unsigned int tot;
vector<edge> G[N];
int dfs_clock, bcc_cnt, dfn[N];
edge S[N*];
int top;
vector<int> a[N*];
int ans[][ + ], sz[];
void init()
{
memset(dfn, , sizeof dfn);
for(int i=;i<=n;i++) G[i].clear();
dfs_clock = ;
bcc_cnt = ;
tot = ;
top = ;
memset(ans, , sizeof ans);
sz[] = ;
}
int test = ;
void tarjan(int u, int fa)
{
dfn[u] = ++dfs_clock;
for(int i=;i<G[u].size();i++)
{
edge e = G[u][i];
int v = e.v, w = e.w;
if(v == fa) continue;
if(!dfn[v])
{
S[++top] = e;
tarjan(v, u);
top--;
}
else if(dfn[v] < dfn[u])
{
bcc_cnt++;
a[bcc_cnt].clear();
a[bcc_cnt].push_back(e.w);
int top1 = top;
for(;;)
{
edge x = S[top1--];
a[bcc_cnt].push_back(x.w);
if(x.u == v) break;
}
}
}
}
bool cmp(int x, int y) {return x > y;}
struct node
{
int id, w;
bool operator < (const node & temp) const
{
return w < temp.w;
}
};
void merge(int *pre, int r, vector<int> &v, int *now)
{
priority_queue<node> Q;
for(int i=;i<v.size();i++) Q.push((node){, pre[] + v[i]});
for(int i=;i<k;i++)
{
sz[(r+)&] = i + ;
node temp = Q.top(); Q.pop();
now[i] = temp.w;
if(temp.id + < sz[r&]) Q.push((node){temp.id+, temp.w-pre[temp.id]+pre[temp.id+]});
if(Q.empty()) break;
}
} int main()
{
int kase = ;
while(scanf("%d%d",&n,&m) == )
{
init();
for(int i=;i<=m;i++)
{
int u, v, w;
scanf("%d%d%d",&u,&v,&w);
G[u].push_back((edge){u, v, w});
G[v].push_back((edge){v, u, w});
tot += w;
}
scanf("%d",&k);
tarjan(, -);
for(int i=;i<=bcc_cnt;i++)
{
sort(a[i].begin(), a[i].end(), cmp);
merge(ans[(i-)&],i-,a[i],ans[i&]);
}
unsigned int sum = ;
for(int i=;i<sz[bcc_cnt&];i++)
{
sum += (unsigned int)(i+) * (unsigned int)(tot-ans[bcc_cnt&][i]);
}
printf("Case #%d: %u\n",kase++,sum);
}
return ;
}

HDU 6041 I Curse Myself ——(仙人掌图,tarjan,转化)的更多相关文章

  1. HDU 6041 - I Curse Myself | 2017 Multi-University Training Contest 1

    和题解大致相同的思路 /* HDU 6041 - I Curse Myself [ 图论,找环,最大k和 ] | 2017 Multi-University Training Contest 1 题意 ...

  2. HDU 6041.I Curse Myself 无向仙人掌图

    I Curse Myself Time Limit: 8000/4000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others) ...

  3. HDU 6041 I Curse Myself(二分+搜索)

    [题目链接] http://acm.hdu.edu.cn/showproblem.php?pid=6041 [题目大意] 给出一个仙人掌图,求第k小生成树 [题解] 首先找到仙人掌图上的环,现在的问题 ...

  4. bzoj 1023: [SHOI2008]cactus仙人掌图 tarjan缩环&&环上单调队列

    1023: [SHOI2008]cactus仙人掌图 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 1141  Solved: 435[Submit][ ...

  5. HDU 3594 Cactus 有向仙人掌图判定

    题意 给出一个有向图,并给出仙人掌图的定义 图本身是强连通的 每条边属于且只属于一个环 判断输入的图是否是强连通的. 分析 杭电OJ上的数据比较弱,网上一些有明显错误的代码也能AC. 本着求真务实的精 ...

  6. hdu 3594 Cactus /uva 10510 仙人掌图判定

    仙人掌图(有向):同时满足:1强连通:2任何边不在俩个环中. 个人理解:其实就是环之间相连,两两只有一个公共点,(其实可以缩块),那个公共点是割点.HDU数据弱,网上很多错误代码和解法也可以过. 个人 ...

  7. HDU 6041 I Curse Myself(点双联通加集合合并求前K大) 2017多校第一场

    题意: 给出一个仙人掌图,然后求他的前K小生成树. 思路: 先给出官方题解 由于图是一个仙人掌,所以显然对于图上的每一个环都需要从环上取出一条边删掉.所以问题就变为有 M 个集合,每个集合里面都有一堆 ...

  8. hdu 3594 强连通好题仙人掌图,对自己的tarjan模板改下用这个

    #include<stdio.h> #include<string.h> #define N 21000 struct node { int v,next; }bian[510 ...

  9. hdu 6041 I Curse Myself

    题目: 点这里OvO http://acm.hdu.edu.cn/showproblem.php?pid=6041 2017 Multi-University Training Contest - T ...

随机推荐

  1. WebApi 身份认 Basic基础认证

    <body> <div style="text-align:center;"> <div>用户名:<input type="te ...

  2. 3_PHP表达式_2_变量

    以下为学习孔祥盛主编的<PHP编程基础与实例教程>(第二版)所做的笔记. PHP变量可分为自定义变量和预定义变量. 以下所谈到的变量均为自定义变量. 1.变量的基本概念 PHP的变量名遵循 ...

  3. MySQL-8.0.16 的安装与配置

    最近老是安装mysql, 但是由于各个环境下文件不互通,所以感觉笔记还是记录在这里比较方便.以下内容,是对网络上大家的笔记的搜集和整理,并经过自己的实践,记录下来.以便,让大家更好.更快的配置mysq ...

  4. Mac命令行指定特定程序打开文件

    如果文件已被指定默认程序 open httpd.conf 指定一个特定程序打开文件 # 用 sublime text 打开 httpd.conf open -a /Applications/Subli ...

  5. linux 安装mysql(rpm文件安装)

    三 卸载旧版本的MySql (没有的话,则跳过此步骤)       1.查看旧版本MySql       rpm -qa | grep mysql       将会列出旧版本MySql的组件列表,如: ...

  6. Linux下相关性能指标数据采集

    1)如何查看某个服务进程所占本机物理内存及百分比情况?可以使用Linux命令行查看,也可以使用脚本实现.如下以查看本机kube-nginx服务进程为例: [root@kevin ~]# pidof k ...

  7. ZZNU - OJ - 2080 : A+B or A-B【暴力枚举】

    2080 : A+B or A-B(点击左侧标题进入zznu原题页面) 时间限制:1 Sec 内存限制:0 MiB提交:8 答案正确:3 提交 状态 讨论区 题目描述 Give you three s ...

  8. 快捷键和功能键、进入DOS命令行的方法、DOS命令讲解、java跨平台原理、JRE和JDK的定义、书写格式

    快捷键和功能键A:键盘功能键* a:Tab* b:Shift* c:Ctrl* d:Alt* e:空格 * f:Enter* g:Window* h:上下左右键* i:PrtSc(PrintScree ...

  9. 22 webpack结合Vue使用的总结

    总结梳理:webpack中如何使用vue: 1.安装vue的包:cnpm i vue -S 2.由于 在webpack中,推荐使用 .vue这个组件模板文件定义组件, 所以,需要安装 能解析这种文件的 ...

  10. js 面向对象之构造器与工厂函数

    字面量模式声明一个对象实例 let m = {name: "lisi", age:15} m.constructor // ƒ Object() { [native code] } ...