题目描述

给定一张n个点,m条双向边的无向图。
你要从1号点走到n号点。当你位于x点时,你需要花1元钱,等概率随机地买到与x相邻的一个点的票,只有通过票才能走到其它点。
每当完成一次交易时,你可以选择直接使用那张票,也可以选择扔掉那张票然后再花1元钱随机买另一张票。注意你可以无限次扔票。
请使用最佳的策略,使得期望花的钱数最少。

输入

第一行包含两个正整数n,m(1<=n,m<=300000),表示点数和边数。
接下来m行,每行两个正整数u,v(1<=u,v<=n),表示一条双向边。
输入数据保证无重边、无自环,且1号点一定可以走到n号点。

输出

输出一行一个实数,即最少的期望花费,当绝对或者相对误差不超过10^{-6}时视为正确。

样例输入

5 8
1 2
1 3
1 4
2 3
2 4
3 5
5 4
2 5

样例输出

4.1111111111


题解

期望dp+堆优化Dijkstra

设 $f[i]$ 表示 $i$ 到终点的期望步数,那么有:$f[n]=0\ ,\ f[x]=\frac{\sum\limits_{(x,y)}\text{min}(f[x],f[y])+1}{d[x]}$ ,其中 $d[x]$ 表示 $x$ 的度数。

套路:对于这种 “初始只有一个点的dp值确定、其它点的dp值与其相邻的点有关” 的图上dp,考虑使用类似最短路的方式转移。

初始的时候除了 $n$ 以外,每个点的 $\text{min}(f[x],f[y])$ 都取 $f[x]$ ,dp值为 $+\infty$ 。

然后从 $n$ 号点开始最短路转移:对于当前的点 $i$ ,如果某个相邻的 $j$ 有 $f[j]>f[i]$ ,则对于 $f[j]$ 的计算来说,$\text{min}(f[j],f[i])$ 取 $f[i]$ 更优。此时更新 $j$ 的dp值,并将 $j$ 加入到待用于更新其它点的集合中。

注意到:如果使用 $f[i]$ 将 $f[j]$ 更新为 $f'[j]$ ,那么显然有 $f[i]\le f'[j]\le f[j]$ (等号在 $f[i]=f[j]$ 时取到),满足堆优化Dijkstra的贪心策略(当前最小的一定不会再被更新到更小),因此可以使用dp值小根堆来维护待用于更新其它点的集合,使用类似堆优化Dijkstra的方式转移即可。

最终的答案就是 $f[1]$ 。

时间复杂度 $O(m\log n)$

#include <queue>
#include <cstdio>
#include <algorithm>
#define N 300010
using namespace std;
typedef pair<double , int> pr;
priority_queue<pr> q;
double s[N] , f[N];
int head[N] , to[N << 1] , next[N << 1] , cnt , vis[N] , d[N] , c[N];
inline void add(int x , int y)
{
to[++cnt] = y , next[cnt] = head[x] , head[x] = cnt;
}
int main()
{
int n , m , i , x , y;
scanf("%d%d" , &n , &m);
for(i = 1 ; i <= m ; i ++ ) scanf("%d%d" , &x , &y) , add(x , y) , add(y , x) , d[x] ++ , d[y] ++ ;
q.push(pr(0 , n));
while(!q.empty())
{
x = q.top().second , q.pop();
if(vis[x]) continue;
vis[x] = 1;
for(i = head[x] ; i ; i = next[i])
if(!vis[to[i]])
c[to[i]] ++ , s[to[i]] += f[x] , f[to[i]] = (s[to[i]] + d[to[i]]) / c[to[i]] , q.push(pr(-f[to[i]] , to[i]));
}
printf("%lf\n" , f[1]);
return 0;
}

【bzoj5197】[CERC2017]Gambling Guide 期望dp+堆优化Dijkstra的更多相关文章

  1. [BZOJ5197] [CERC2017]Gambling Guide

    [BZOJ5197] [CERC2017]Gambling Guide 题目链接 https://www.lydsy.com/JudgeOnline/problem.php?id=5197 Solut ...

  2. 【bzoj1097】[POI2007]旅游景点atr 状压dp+堆优化Dijkstra

    题目描述 FGD想从成都去上海旅游.在旅途中他希望经过一些城市并在那里欣赏风景,品尝风味小吃或者做其他的有趣的事情.经过这些城市的顺序不是完全随意的,比如说FGD不希望在刚吃过一顿大餐之后立刻去下一个 ...

  3. Luogu4745/Gym101620G CERC2017 Gambling Guide 期望、DP、最短路

    传送门--Luogu 传送门--Vjudge 设\(f_x\)为从\(x\)走到\(N\)的期望步数 如果没有可以不动的限制,就是隔壁HNOI2013 游走 如果有可以不动的限制,那么\(f_x = ...

  4. BZOJ5197:[CERC2017]Gambling Guide(最短路,期望DP)

    Description 给定一张n个点,m条双向边的无向图. 你要从1号点走到n号点.当你位于x点时,你需要花1元钱,等概率随机地买到与x相邻的一个点的票,只有通过票才能走到其它点. 每当完成一次交易 ...

  5. 【BZOJ5197】Gambling Guide (最短路,期望)

    [BZOJ5197]Gambling Guide (最短路,期望) 题面 BZOJ权限题 洛谷 题解 假设我们求出了每个点的期望,那么对于一个点,只有向期望更小的点移动的时候才会更新答案. 即转移是: ...

  6. 【bzoj4016】[FJOI2014]最短路径树问题 堆优化Dijkstra+DFS树+树的点分治

    题目描述 给一个包含n个点,m条边的无向连通图.从顶点1出发,往其余所有点分别走一次并返回. 往某一个点走时,选择总长度最短的路径走.若有多条长度最短的路径,则选择经过的顶点序列字典序最小的那条路径( ...

  7. BZOJ 3040 最短路 (堆优化dijkstra)

    这题不是裸的最短路么?但是一看数据范围就傻了.点数10^6,边数10^7.这个spfa就别想了(本来spfa就是相当不靠谱的玩意),看来是要用堆优化dijkstra了.但是,平时写dijkstra时为 ...

  8. UVA - 11374 - Airport Express(堆优化Dijkstra)

    Problem    UVA - 11374 - Airport Express Time Limit: 1000 mSec Problem Description In a small city c ...

  9. BZOJ5415[Noi2018]归程——kruskal重构树+倍增+堆优化dijkstra

    题目描述 本题的故事发生在魔力之都,在这里我们将为你介绍一些必要的设定. 魔力之都可以抽象成一个 n 个节点.m 条边的无向连通图(节点的编号从 1 至 n).我们依次用 l,a 描述一条边的长度.海 ...

随机推荐

  1. 再论WPF中的UseLayoutRounding和SnapsToDevicePixels

    原文:再论WPF中的UseLayoutRounding和SnapsToDevicePixels 版权声明:.net/web/医疗技术的木子纵横的个人分享 https://blog.csdn.net/m ...

  2. 简单的Slony-I设置实例

    磨砺技术珠矶,践行数据之道,追求卓越价值 回到上一级页面: PostgreSQL集群方案相关索引页     回到顶级页面:PostgreSQL索引页 参考如下链接: http://lets.postg ...

  3. [BZOJ4383][POI2015] Pustynia-[线段树+dp+拓扑排序]

    Description 给定一个长度为n的正整数序列a,每个数都在1到10^9范围内,告诉你其中s个数,并给出m条信息,每条信息包含三个数l,r,k以及接下来k个正整数,表示a[l],a[l+1],. ...

  4. Qt开发者关于QThread的咆哮——你们都用错了

    Qt开发者关于QThread的咆哮——你们都用错了 我们(Qt用户)正广泛地使用IRC来进行交流.我在Freenode网站挂出了#qt标签,用于帮助大家解答问题.我经常看到的一个问题(这让我不厌其烦) ...

  5. 【CF833E】Caramel Clouds

    [CF833E]Caramel Clouds 题面 洛谷 题目大意: 天上有\(n\)朵云,每朵云\(i\)会在时间\([li,ri]\)出现,你有\(C\)个糖果,你可以花费\(c_i\)个糖果让云 ...

  6. PHP5.4 连接 SQL SERVER 2008

    PHP链接sqlserver需要先安装驱动,不是先把dll放到ext下面,一重启服务器就完事了. 本地环境: XAMPP 1.8.2 PHP 5.4.31 SQL SERVER 2008 R2 使用的 ...

  7. 【MYSQL权限】数据库权限部署

    背景:没有划分数据库权限,所有人共用一个账号 本人公司现有的数据库账号分布情况: 所有人用一个账号(包括程序里面访问数据库的的配置文件里面的账号),该账号除删库权限,其他权限大部分都有. 这样非数据库 ...

  8. 查询系统日期和时间(mysql)

    select current_date  --不带时间select sysdate()   或 SELECT NOW();  --带时间

  9. MySQL5.6.14从安装到启动全过程

    1.下载 地址:http://dev.mysql.com/downloads/mysql/ 这里选择的是Linux-Generic平台,下载了MySQL-5.6.14-1.linux_glibc2.5 ...

  10. JUC——线程同步锁(锁处理机制简介)

    锁处理机制简介 juc的开发框架解决的核心问题是并发访问和数据安全操作问题,当进行并发访问的时候如果对于锁的控制不当,就会造成死锁这样的阻塞问题. 为了解决这样的缺陷,juc里面重新针对于锁的概念进行 ...