HZOI2019 B. 那一天她离我而去 最小环
题目大意:https://www.cnblogs.com/Juve/articles/11219089.html
那一天,我们......行啦,不要帮出题人脑补画面了,我们来正经的题解
我们发现我们可以把与1号节点相连的所有节点取出,如果我们把最小环在1号节点处断开,那么最小环断成的链一定是以这些节点中的某一个节点作为起点,另一个节点作为终点的一条路路径。
如果不考虑时间复杂度,我们完全可以枚举作为起点的节点,每次都跑一遍最短路来更新答案。
但是上面的做法肯定会爆炸,所以我们考虑如何降低复杂度。
我们考虑把所有的节点分为两组,一组中的所有点作为起点,另一组中的所有点作为终点,一起跑最短路,更新答案。
如此我们发现只要我们能够保证真正贡献答案的一对节点会在某一次分组当中被分到不同组,我们就可以保证算法的正确性。
因为起点与终点的编号肯定不相同,于是我们可以按照二进制分组,枚举每个二进制位,按照当前二进制位的0/1情况来进行分组。
我看好像没有人用这种方法的,其实dij就可以过,用dij求1号节点开始的最小环
别告诉我你不会求最小环。
我们枚举1号点连接的每一条边,设起点为fr[i],终点为to[i],
先把这条边权变成0x3f3f3f3f,跑dij,求出此时fr[i]到to[i]的最短路,再加上原来这条边的权值就是一个环的大小,
更新答案:ans=min(dis[to[i]]+w[i]);
就是把fr[i]和to[i]间的边断开后两点间的最短路加上原来两点间的距离取最小值
原来博主想用tarjan求边双,然后在1号节点所在的边双中跑dij,但时间并没有下去
还有注意给边编号从2开始,这样i和i^1是一对双向边
本来一道很有思维量的题被做成了dijkstra模板(好像没人用正解打)
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#define ll long long
#define MAXN 10005
#define MAXM 40005
using namespace std;
ll t,n,m,ans=0x3f3f3f3f;
ll pre[MAXN],tot_e=1,to[MAXM<<1],nxt[MAXM<<1],w[MAXM<<1];
void add(ll u,ll v,ll d){
tot_e++,to[tot_e]=v,nxt[tot_e]=pre[u],pre[u]=tot_e,w[tot_e]=d;
}
ll dis[MAXN];
priority_queue< pair<ll, ll> > q;
bool visit[MAXN];
void dijkstra(ll x){
memset(dis,0x3f,sizeof(dis));
dis[x]=0;
memset(visit,0,sizeof(visit));
q.push(make_pair(-dis[x],x));
while(!q.empty()){
ll y=q.top().second;q.pop();
if(visit[y]) continue;
visit[y]=1;
for(ll i=pre[y];i;i=nxt[i]){
ll v=to[i],z=w[i];
if(dis[v]>dis[y]+z){
dis[v]=dis[y]+z;
q.push(make_pair(-dis[v],v));
}
}
}
}
int main(){
scanf("%lld",&t);
while(t--){
scanf("%lld%lld",&n,&m);
for(ll i=1,u,v,d;i<=m;i++){
scanf("%lld%lld%lld",&u,&v,&d);
add(u,v,d),add(v,u,d);
}
for(ll i=pre[1];i;i=nxt[i]){
ll temp=w[i];
w[i]=w[i^1]=0x3f3f3f3f;
dijkstra(1);
ans=min(ans,dis[to[i]]+temp);
w[i]=w[i^1]=temp;
}
if(ans==0x3f3f3f3f) ans=-1;
printf("%lld\n",ans);
ans=0x3f3f3f3f;
tot_e=1;
memset(pre,0,sizeof(pre));
}
return 0;
}
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#define ll long long
#define MAXN 10005
#define MAXM 40005
using namespace std;
ll t,n,m,ans=0x3f3f3f3f;
ll pre[MAXN],tot_e=,to[MAXM<<],nxt[MAXM<<],w[MAXM<<];
void add(ll u,ll v,ll d){
tot_e++,to[tot_e]=v,nxt[tot_e]=pre[u],pre[u]=tot_e,w[tot_e]=d;
}
bool vis[MAXM<<];
void dfs(ll x,ll res){
if(res>ans) return ;
if(x==){
if(res!=){
ans=min(ans,res);
return ;
}
}
for(ll i=pre[x];i;i=nxt[i]){
if(!vis[i]){
vis[i]=,vis[i^]=;
dfs(to[i],res+w[i]);
vis[i]=,vis[i^]=;
}
}
}
ll dfn[MAXN],low[MAXN],dfs_order=;
bool is_bridge[MAXM<<];
void tarjan(ll x,ll in_edge){
dfn[x]=low[x]=++dfs_order;
for(ll i=pre[x];i;i=nxt[i]){
ll y=to[i];
if(!dfn[y]){
tarjan(y,i);
low[x]=min(low[x],low[y]);
if(low[y]>low[x])
is_bridge[i]=is_bridge[i^]=;
}
else if(i!=(in_edge^))
low[x]=min(low[x],dfn[y]);
}
}
bool belong[MAXN];
void DFS(int x){
belong[x]=;
for(int i=pre[x];i;i=nxt[i]){
int y=to[i];
if(belong[y]||is_bridge[i]) continue;
DFS(y);
}
}
ll dis[MAXN];
priority_queue< pair<ll, ll> > q;
bool visit[MAXN];
void dijkstra(ll x){
memset(dis,0x3f,sizeof(dis));
dis[x]=;
memset(visit,,sizeof(visit));
q.push(make_pair(-dis[x],x));
while(!q.empty()){
ll y=q.top().second;q.pop();
if(visit[y]) continue;
visit[y]=;
for(ll i=pre[y];i;i=nxt[i]){
ll v=to[i],z=w[i];
if(dis[v]>dis[y]+z){
dis[v]=dis[y]+z;
q.push(make_pair(-dis[v],v));
}
}
}
}
int main(){
scanf("%lld",&t);
while(t--){
scanf("%lld%lld",&n,&m);
if(n==m){
for(ll i=,u,v,d;i<=m;i++){
scanf("%lld%lld%lld",&u,&v,&d);
add(u,v,d),add(v,u,d);
}
dfs(,);
if(ans==0x3f3f3f3f) ans=-;
printf("%lld\n",ans);
ans=0x3f3f3f3f;
memset(pre,,sizeof(pre));
tot_e=;
}else{
for(ll i=,u,v,d;i<=m;i++){
scanf("%lld%lld%lld",&u,&v,&d);
add(u,v,d),add(v,u,d);
}
for(ll i=;i<=n;i++){
if(!dfn[i]) tarjan(i,);
}
DFS();
for(ll i=pre[];i;i=nxt[i]){
if(is_bridge[i]||!belong[to[i]]) continue;
ll temp=w[i];
w[i]=w[i^]=0x3f3f3f3f;
dijkstra();
ans=min(ans,dis[to[i]]+temp);
w[i]=w[i^]=temp;
}
if(ans==0x3f3f3f3f) ans=-;
printf("%lld\n",ans);
ans=0x3f3f3f3f;
tot_e=,dfs_order=;
memset(pre,,sizeof(pre));
memset(dfn,,sizeof(dfn));
memset(is_bridge,,sizeof(is_bridge));
}
}
return ;
}
tarjan的复杂算法
更多算法:
https://www.cnblogs.com/Juve/articles/11220105.html
HZOI2019 B. 那一天她离我而去 最小环的更多相关文章
- HZOI2019 A. 那一天我们许下约定 dp
题目大意:https://www.cnblogs.com/Juve/articles/11219089.html 读这道题的题目让我想起了... woc我到底在想什么?好好写题解,现在不是干那个的时候 ...
- HZOI2019 超级树 dp
题面:https://www.cnblogs.com/Juve/articles/11207540.html(密码)————————————————>>> 题解: 官方题解: 考虑d ...
- HZOI2019 砍树 整除分块
题目链接:https://www.cnblogs.com/Juve/articles/11207540.html(密码你懂的)——————————>> 这题... 一开始想的二分,但此题不 ...
- HZOI2019 星际旅行 欧拉路
题目大意:https://www.cnblogs.com/Juve/articles/11207540.html—————————> 题解:网上都是一句话题解:将所有的边拆成两条,问题变成去掉两 ...
- HZOI2019熟练剖分(tree)
题目大意:https://www.cnblogs.com/Juve/articles/11186805.html 题解: 先给出官方题解: 其实这题跟期望没什么关系,因为E=$\sum_\limits ...
- HZOI2019建造游乐园(play)组合数学,欧拉图
题目:https://www.cnblogs.com/Juve/articles/11186805.html(密码是我的一个oj用户名) solution: 反正我是想不出来... 题目大意就是要求出 ...
- HZOI2019序列
题目链接:https://www.cnblogs.com/Juve/articles/11186805.html(密码是我的一个oj用户名) 题解: 这题我考试打的暴力,只有5分. 一开始理解错题意了 ...
- 【暑假集训】HZOI2019 Luogu P1006 传纸条 二三四维解法
写三次丢失两次,我谔谔,以后再不在博客园先保存我就去死 题目内容 洛谷链接 小渊和小轩是好朋友也是同班同学,他们在一起总有谈不完的话题.一次素质拓展活动中,班上同学被安排坐成一个\(m\)行.\(n\ ...
- 【暑假集训】HZOI2019 水站 多种解法
题目内容 已知有一个\(n\)层的水站: \(W_i\)表示未操作之前第\(i\)层的已有水量: \(L_i\)表示第\(i\)个水站能够维持或者储存的水的重量: 表示在第\(P_i\)层进行减压放水 ...
随机推荐
- 用VC++MFC做文本编辑器(单文档模式)
用VC++MFC做文本编辑器(单文档模式) 原来做过一个用对话框实现的文本编辑器,其实用MFC模板里面的单文档模板也可以做,甚至更加方便,适合入门级的爱好者试试,现介绍方法如下: < xmlna ...
- duilib教程之duilib入门简明教程6.XML配置界面
前面那些教程都是为了让小伙伴们从win32.MFC过渡到duilib,让大家觉得duilib不是那么陌生,如果大家现在还对duilib非常陌生的话,那就说明前面的教程做得不好,请大家在下面留言,我会一 ...
- NOI2014
听说14,15年的题是最简单的,然后除了提答以外的不那么水的题都是以前讲过.做过的,都比较好想到,但是我实现起来却有各种Bug,也完全不能在5h里AC...太弱了 [NOI2014]起床困难综合症 纯 ...
- linux安装splunk-enterprise
一.介绍 Splunk是一款功能强大,功能强大且完全集成的软件,用于实时企业日志管理,可收集,存储,搜索,诊断和报告任何日志和机器生成的数据,包括结构化,非结构化和复杂的多行应用程序日志. 它允许您以 ...
- 手机端判断安卓,iso,微信
var uaContains = function (key) { return navigator.userAgent.toLowerCase().indexOf(key.toLowerCase() ...
- 进程通信类型 管道是Linux支持的最初Unix IPC形式之一
管道 Linux环境进程间通信(一) https://www.ibm.com/developerworks/cn/linux/l-ipc/part1/index.html 管道及有名管道 郑彦兴200 ...
- Java 高级面试知识点汇总!
1.常用设计模式 单例模式:懒汉式.饿汉式.双重校验锁.静态加载,内部类加载.枚举类加载.保证一个类仅有一个实例,并提供一个访问它的全局访问点. 代理模式:动态代理和静态代理,什么时候使用动态代理. ...
- 03_springboot2.x日志处理
1.日志框架 市场上存在非常多的日志框架.JUL(java.util.logging),JCL(Apache Commons Logging),Log4j,Log4j2,Logback.SLF4j ...
- Cefsharp实现快捷键功能
原文:Cefsharp实现快捷键功能 1 . 实现IKeyboardHandler接口 public class KeyBoardHander : IKeyboardHandler { public ...
- 7款外观迷人的HTML5/CSS3 3D特效按钮特效
下面我整理了7款外观都十分迷人的HTML5/CSS3 3D按钮特效,有几个还挺实用的,分享给大家. 1.CSS3超酷3D弹性按钮 按钮实现非常简单 之前我们分享过几款不错的CSS3 3D立体按钮,比如 ...