题意与分析

定义走到每条边的期望为\(e_i\),一开始的想法是给定一个\(\large\sum_{i=1}^n e_i a_i\),求一个a的排列使得这个和最小。问题在于这样等于没对题目作分析,而且题目的难度没有被转化降低。于是(在高人指点下)我们想到,如果先求出\(e_i\),然后按照从小到大的顺序贪心的编号,问题就直接转化成求走到每个边的期望。

边的期望是一个新操作,但是其实不难:定义走到点的期望是\(f_i\),考虑一条边\((u, v)\),对于这条边而言,只有从u和从v才能走到这条边,那么它的期望就是\(\large e_i=\frac{f_u}{degree_u}+\frac{f_v}{degree_v}\)。于是问题又转化成走到各个点的期望。

如果这是个DAG,那么问题是一个dp(\(dp[j]\)表示从j到n的期望长度,\(dp[i] = \sum_{i\to j} \frac{dp[j]+1}{degree_i}\),具体问题见BZOJ-3036)。问题是这题并不是,场面有点尴尬。但是上面DAG的方程加起来共有n个,而我们要求n-1个解,这提示了我们用高斯消元解决这个问题。用高斯消元的话我们就把公式变形一下:

\[e_i = \sum_{j=1}^n p_{i,j}e_{j} , 2\le i \le n
\]

其中\(p_{i,j}\)表示从j走到i的概率,对于第一个点该式子的右边还要加上一个1(因为一开始就在这个点上了,不妨思考下平凡的情况)。这样一来就可以用高斯消元解决这一题了。

问题的逐步转化是这一题的关键。

代码

#include <bits/stdc++.h>

using namespace std;

vector<pair<int, int>> edges;
vector<int> G[505]; double arr[505][505];
int main() {
int n, m;
while (cin >> n >> m) {
for (int i = 1, u, v; i <= m; ++i) {
cin >> u >> v;
if (u > v)
swap(v, u);
edges.push_back(make_pair(u, v));
G[u].push_back(v);
G[v].push_back(u);
}
memset(arr, 0, sizeof(arr));
for (int i = 1; i <= n; ++i)
arr[i][i] = -1.0;
arr[1][n + 1] = -1.0;
for (int i = 1; i < n; i++) {
for (int j = 0; j < G[i].size(); ++j)
arr[G[i][j]][i] += 1.0 / (int)G[i].size();
}
for (int i = 1; i <= n; ++i) {
int idx = i;
for (int j = i + 1; j <= n; ++j)
if (fabs(arr[j][i]) > fabs(arr[idx][i]))
idx = j;
assert(fabs(arr[idx][i]) > 1e-10);
if (idx != i)
for (int j = i; j <= n + 1; ++j)
swap(arr[i][j], arr[idx][j]);
for (int j = 1; j <= n; ++j)
if (i != j) {
double t = arr[j][i] / arr[i][i];
for (int k = i; k <= n + 1; ++k)
arr[j][k] -= arr[i][k] * t;
}
}
/*
for (int i = 1; i <= n; ++i) {
for (int j = 1; j <= n + 1; ++j) {
cout << arr[i][j] << " ";
}
cout << endl;
}
*/
double e_node[505];
double e_edge[500 * 500 / 2 + 5];
memset(e_edge, 0, sizeof(e_edge));
memset(e_node, 0, sizeof(e_node));
for (int i = 1; i <= n; ++i) {
e_node[i] = arr[i][n + 1] / arr[i][i];
}
for (int i = 0; i < edges.size(); ++i) {
e_edge[i] += e_node[edges[i].first] / G[edges[i].first].size();
if (edges[i].second != n)
e_edge[i] += e_node[edges[i].second] / G[edges[i].second].size();
}
sort(e_edge, e_edge + m);
double ans = 0;
for (int i = 0; i < m; ++i)
ans += e_edge[i] * (m - i);
cout << fixed << setprecision(3) << ans << endl;
}
return 0;
}

「专题训练」游走(BZOJ-3143)的更多相关文章

  1. 游走 bzoj 3143

    游走(2s 128MB)walk [问题描述] [输入格式] [输出格式] [样例输入] 3 3 2 3 1 2 1 3 [样例输出] 3.333 [样例说明] 题解: 主要算法:贪心:高斯消元: 题 ...

  2. 「HNOI 2013」游走

    题目链接 戳我 \(Solution\) 首先申明几个变量: f[x]:到点x的概率, vis[x]:x点的度 dp[x][y]:(x,y)这条边的概率 number[x][y]:x这条边的编号 下面 ...

  3. 「专题训练」k-Tree(CodeForces Round #247 Div.2 C)

    题意与分析(Codeforces-431C) 题意是这样的:给出K-Tree--一个无限增长的树,它的每个结点都恰有\(K\)个孩子,每个节点到它\(K\)个孩子的\(K\)条边的权重各为\(1,2, ...

  4. 「专题训练」Air Raid(HDU-1151)

    题目 在一个城市里有\(n\)个地点和\(k\)条道路,道路是无环的(也就是说一定可以二分染色--回路长度为偶数0),现在伞兵需要去n个地点视察,只能沿着路的方向走,问最少需要多少伞兵. 分析 这是什 ...

  5. 「专题训练」Machine Schedule(HDU-1150)

    题意 在一个工厂,有两台机器\(A, B\)生产产品.\(A\)机器有\(n\)种工作模式(模式\(0\),模式\(1\)--模式\(n-1\)).\(B\)机器有\(m\)种工作模式(模式\(0\) ...

  6. 「专题训练」Collecting Bugs(POJ-2096)

    题意与分析 题意大致是这样的:给定一个\(n\times s\)的矩阵,每次可以随机的在这个矩阵内给一个格子染色(染过色的仍然可能被选中),问每一行和每一列都有格子被染色的次数的期望. 这题如果从概率 ...

  7. 「专题训练」Hard problem(Codeforces Round #367 Div. 2 C)

    题意与分析 题意:给出\(n\)个字符串,可以反转任意串,反转每个串都有其对应的花费\(c_i\).经过操作后是否能满足字符串\(\forall i \in [1,n] \text{且} i \in ...

  8. 「专题训练」Boredom(CodeForces Round #260 Div.1 A)

    题意(Codeforces-455A) 给你\(n\)个数,你每次可以选择删除去一个数\(x\)获得\(x\)分,但是所有为\(x+1\)和\(x-1\)的数都得删去.问最大获得分数. 分析 这是一条 ...

  9. 「HNOI2013」游走

    「HNOI2013」游走 题目描述 一个无向连通图,顶点从 \(1\) 编号到 \(N\) ,边从 \(1\) 编号到 \(M\) .小 \(Z\) 在该图上进行随机游走,初始时小 \(Z\) 在 \ ...

随机推荐

  1. Spring 源代码阅读之声明式事务

    事务控制流程 例如对如下代码进行事务控制 class service1{ method1(){ method2(); } } class service2{ method2(); } 原理:建立一个m ...

  2. rimraf命令 递归删除目录所有文件

    使用webpack build文件项目时每次都会生成一个dist目录,有时需要把dist目录里的所以旧文件全部删掉, 除了可以使用rm -rf /dist/命令删除外,还可以使用rimraf /dis ...

  3. leetcode第一刷_N-Queens

    八皇后问题应该是回溯法的教学典范.在本科的时候,有一门课叫面向对象.最后的附录有这个问题的源码.当时根本不懂编程,照抄下来,执行一下出了结果都非常开心,哎. 皇后们的限制条件是不能同行同列,也不能同对 ...

  4. 将项目发布到Maven中央仓库的不完整纪要

    背景 有几个Utils性质的Jar需要跨项目引用,原本想部署私有Maven仓库,后来感觉太麻烦,索性直接发布到中央库,引用时也方便. 发布成功之后,觉得某些细节还是有必要记录一下. 资源 Sonaty ...

  5. Docker存储方式选型建议

    转自:https://segmentfault.com/a/1190000007168476 第一部分 问题诊断 事情从一次实施项目说起,我们需要帮助客户将他们的应用容器化并在数人云平台上发布此应用. ...

  6. ZOJ 3983 Crusaders Quest(思维题)

    C - Crusaders Quest Time Limit:1000MS     Memory Limit:65536KB     64bit IO Format:%lld & %llu S ...

  7. POJ 1080( LCS变形)

    题目链接: http://poj.org/problem?id=1080 Human Gene Functions Time Limit: 1000MS   Memory Limit: 10000K ...

  8. http协议中的keeplive是做什么的?它的适应场景是什么?

    1.Http底层也是通过TCP传输的. 2.HTTP keep-alive Http是一个”请求-响应”协议,它的keep-alive主要是为了让多个http请求共享一个Tcp连接,以避免每个Http ...

  9. 第一次码java感想及前三次作业总结

    写在前面 嗯,首先是java,这学期第一次oo作业布置下来的周末才开始看的,第一次作业因此写得有些手忙脚乱.不过大概看了一遍后发现比c好用,入门更简单吧,好多操作直接import一下就能用了,码代码的 ...

  10. SMARTFORMS关闭失败

    用户要调整表单样式,结果调整完发现打印时报错. 检查表单后发现,是因为用户要求删除表单中的一个单元格,但是删除TEMPLATE中的一个格子后,忘了调整后续单元格内容输出的位置.导致输出错误.