BZOJ 3036: 绿豆蛙的归宿 期望 + 拓扑排序
随着新版百度空间的下线,Blog宠物绿豆蛙完成了它的使命,去寻找它新的归宿。
给出一个有向无环的连通图,起点为1终点为N,每条边都有一个长度。绿豆蛙从起点出发,走向终点。
到达每一个顶点时,如果有K条离开该点的道路,绿豆蛙可以选择任意一条道路离开该点,并且走向每条路的概率为 1/K 。
现在绿豆蛙想知道,从起点走到终点的所经过的路径总长度期望是多少?
题解:
设 $f_{i}$ 表示 $i$ 号节点走向终点还需期望的步数.
记忆化搜索一下即可.
Code:
#include <bits/stdc++.h> #define setIO(s) freopen(s".in","r",stdin) #define maxn 200003 using namespace std; queue <int> Q; int n, m, edges; int hd[maxn], to[maxn], nex[maxn], deg[maxn], done[maxn]; double val[maxn], f[maxn], k[maxn]; void add(int u, int v, double c) { nex[++edges] = hd[u], hd[u] = edges, to[edges] = v, val[edges] = c; } int main() { // setIO("input"); scanf("%d%d",&n,&m); for(int i = 1; i <= m; ++i) { int a, b; double c; scanf("%d%d%lf",&a,&b,&c), add(b, a, 1.0*c), ++deg[a], ++k[a]; } Q.push(n); while(!Q.empty()) { int u = Q.front(); Q.pop(); for(int i = hd[u]; i ; i = nex[i]) { int v = to[i]; deg[v]--; f[v] += (f[u] + val[i]) / (1.0 * k[v]); if(!deg[v]) Q.push(v); } } printf("%.2f",f[1]); return 0; }