Codeforces Round #130 (Div. 2) C - Police Station 最短路+dp
题目链接:
http://codeforces.com/problemset/problem/208/C
C. Police Station
time limit per test:2 secondsmemory limit per test:256 megabytes
#### 问题描述
> The Berland road network consists of n cities and of m bidirectional roads. The cities are numbered from 1 to n, where the main capital city has number n, and the culture capital — number 1. The road network is set up so that it is possible to reach any city from any other one by the roads. Moving on each road in any direction takes the same time.
>
> All residents of Berland are very lazy people, and so when they want to get from city v to city u, they always choose one of the shortest paths (no matter which one).
>
> The Berland government wants to make this country's road network safer. For that, it is going to put a police station in one city. The police station has a rather strange property: when a citizen of Berland is driving along the road with a police station at one end of it, the citizen drives more carefully, so all such roads are considered safe. The roads, both ends of which differ from the city with the police station, are dangerous.
>
> Now the government wonders where to put the police station so that the average number of safe roads for all the shortest paths from the cultural capital to the main capital would take the maximum value.
#### 输入
> The first input line contains two integers n and m (2 ≤ n ≤ 100, ) — the number of cities and the number of roads in Berland, correspondingly. Next m lines contain pairs of integers vi, ui (1 ≤ vi, ui ≤ n, vi ≠ ui) — the numbers of cities that are connected by the i-th road. The numbers on a line are separated by a space.
>
> It is guaranteed that each pair of cities is connected with no more than one road and that it is possible to get from any city to any other one along Berland roads.
#### 输出
> Print the maximum possible value of the average number of safe roads among all shortest paths from the culture capital to the main one. The answer will be considered valid if its absolute or relative inaccuracy does not exceed 10 - 6.
#### 样例
> **sample input**
> 4 4
> 1 2
> 2 4
> 1 3
> 3 4
>
> **sample output**
> 1.000000000000
题意
给你n个点(编号为1到n),m条边的有向图(无环,无重边,每个点都与其他点连通),现在要在一个点上建一个警察局,一条边,只要有一端与警察局相连,它就是安全的路,否则它就是不安全的路,现在问在哪个点建警察局能使从1到n的每条最短路上平均的安全路的条数(sigma(每条最短路上的安全路条数)/不同的最短路的条数)最多。
题解
首先跑一遍单源最短路求出所有最短路组成的DAG图g1,然后在DAG上dp两次,其中dp[i]表示从n到i的最短路条数,dp2[i]表示从1到i的最短路条数。
这样不同的最短路的条数就等于dp[1]或dp2[n];
由于只有100个点,所以我们暴力枚举在2到n-1哪个点设警察局(在起点和终点设的话,平均的安全路的条数刚好会等于1)。每个警察局只会影响到它的邻边,我们现在把邻边分为两类(在g1中),一类以x为终点的边,一类为以x为起点的边,枚举所有的边,对于第一类边(u,x),贡献值为dp2[u] * dp[x]。
对于第二类边(x,v),贡献值为dp2[x] * dp[v]。sigma(每条最短路上的安全路条数)=sigma(每条边的贡献值)。
所以最后的答案就是max(sigma_i(每条边的贡献值))/dp[1]。
(sigma_i表示第i条边设警察局时的sigma(每条边的贡献值),sigma表示求和符号)
代码
#include<iostream>
#include<cstdio>
#include<cstring>
#include<vector>
#include<algorithm>
#include<map>
#include<queue>
using namespace std;
typedef long long LL;
const int maxn = 222;
int n, m;
vector<int> G[maxn];
//g1表示从1到n的所有最短路组成的DAG图。
vector<int> g1[maxn], g2[maxn];
int inq[maxn], d[maxn];
void spfa(int s) {
memset(d, 0x3f, sizeof(d));
queue<int> pq;
inq[s] = 0; d[s] = 0; pq.push(s);
while (!pq.empty()) {
int u = pq.front(); pq.pop();
inq[u] = 0;
for (int i = 0; i<G[u].size(); i++) {
int v = G[u][i];
if (d[v]>d[u] + 1) {
d[v] = d[u] + 1;
if (!inq[v]) inq[v] = 1, pq.push(v);
g2[v].clear();
g2[v].push_back(u);
}
else if (d[v] == d[u] + 1) {
g2[v].push_back(u);
}
}
}
}
void get_g1() {
for (int u = 1; u <= n; u++) {
// printf("%d: ",u);
for (int i = 0; i<g2[u].size(); i++) {
int v = g2[u][i];
// printf("%d ",v);
g1[v].push_back(u);
}
// puts("");
}
}
LL dp[maxn];//dp[i]表示从n到i之间的最短路数
LL dfs(int u) {
if (dp[u]) return dp[u];
for (int i = 0; i<g1[u].size(); i++) {
int v = g1[u][i];
dp[u] += dfs(v);
}
return dp[u];
}
LL dp2[maxn]; //dp2[i]表示从1到i之间的最短路数
LL dfs2(int u) {
if (dp2[u]) return dp2[u];
for (int i = 0; i<g2[u].size(); i++) {
int v = g2[u][i];
dp2[u] += dfs2(v);
}
return dp2[u];
}
LL solve() {
LL ret = dp[1];
for (int i = 2; i<n; i++) {
LL sum = 0;
for (int j = 0; j<g1[i].size(); j++) {
int v = g1[i][j];
sum += dp[v] * dp2[i];
}
for (int j = 0; j<g2[i].size(); j++) {
int v = g2[i][j];
sum += dp2[v] * dp[i];
}
ret = max(ret, sum);
}
return ret;
}
int main() {
scanf("%d%d", &n, &m);
while (m--) {
int u, v; scanf("%d%d", &u, &v);
G[u].push_back(v);
G[v].push_back(u);
}
spfa(1);
get_g1();
memset(dp, 0, sizeof(dp));
dp[n] = 1;
LL fenmu = dfs(1);
memset(dp2, 0, sizeof(dp2));
dp2[1] = 1;
dfs2(n);
LL fenzi = solve();
printf("%.12lf\n", fenzi*1.0 / fenmu);
return 0;
}
乱七八糟
统计安全边的时候各种奇葩的想法,组合数学没学好,硬伤orz。
Codeforces Round #130 (Div. 2) C - Police Station 最短路+dp的更多相关文章
- Codeforces Round #130 (Div. 2) C. Police Station
题目链接:http://codeforces.com/contest/208/problem/C 思路:题目要求的是经过1~N的最短路上的某个点的路径数 / 最短路的条数的最大值.一开始我是用spf ...
- Codeforces Round #267 (Div. 2) C. George and Job(DP)补题
Codeforces Round #267 (Div. 2) C. George and Job题目链接请点击~ The new ITone 6 has been released recently ...
- Codeforces Round #408 (Div. 2) D - Police Stations
地址:http://codeforces.com/contest/796/problem/D 题目: D. Police Stations time limit per test 2 seconds ...
- Codeforces Round #130 (Div. 2)
A. Dubstep 字符串模拟. string.find()用法 string str; size_t pos = str.find("WUB"); // 返回匹配的第一个位置 ...
- Codeforces Round #130 (Div. 2) A. Dubstep
题目链接: http://codeforces.com/problemset/problem/208/A A. Dubstep time limit per test:2 secondsmemory ...
- Codeforces Round #244 (Div. 2) A. Police Recruits
题目的意思就是找出未能及时处理的犯罪数, #include <iostream> using namespace std; int main(){ int n; cin >> ...
- Codeforces Round #408 (Div. 2) D. Police Stations(最小生成树+构造)
传送门 题意 n个点有n-1条边相连,其中有k个特殊点,要求: 删去尽可能多的边使得剩余的点距特殊点的距离不超过d 输出删去的边数和index 分析 比赛的时候想不清楚,看了别人的题解 一道将1个联通 ...
- Codeforces Round #287 (Div. 2) E. Breaking Good 最短路
题目链接: http://codeforces.com/problemset/problem/507/E E. Breaking Good time limit per test2 secondsme ...
- Codeforces Round #343 (Div. 2) C. Famil Door and Brackets dp
C. Famil Door and Brackets 题目连接: http://www.codeforces.com/contest/629/problem/C Description As Fami ...
随机推荐
- 使用CSS创建有图标的网站导航菜单
在我创建的每一个互联网应用中,我都试图避免创建完全由图片组成的菜单.在我看来,网页菜单系统中应该使用文字.这样做也会让菜单变得更干净利落.清晰和易读,不用考虑应用程序如何读取它,以及页面放大的时候也不 ...
- Filestream读取或写入文件
using System.IO;//引用 System.IO namespace filestream { public partial class Form1 : Form { public For ...
- 前端基础 - Defer对象
参考:http://www.ruanyifeng.com/blog/2011/08/a_detailed_explanation_of_jquery_deferred_object.html < ...
- Web调用ExE
把这个文件导入注册表,那么我们在浏览器中输入PrintLabel://1022,那么就会自动调用C:\\Program Files\\xxx有限公司\\Sellercube Label Maker\\ ...
- VS2008无法切换到视图设计器
编写人:CC阿爸 2014-2-17 近来用于干活的笔记本电脑实在太慢了,在领导的安排下,有幸更换了一台配置好的电脑.经过一天的努力,所有之前的开发软件都安装完成了.并且OS从xp升级到win7.SQ ...
- 小菜的系统框架界面设计-灰姑娘到白雪公主的蜕变(工具条OutLookBar)
灰姑娘本身也有自已的优点,但是却可能因为外貌不讨人喜欢,要变成白雪公主却需要有很多勇气和决心去改变自已: 有一颗善良的心 讨人喜爱的外貌 --蜕变--> 我这里讲的是一个工具条的蜕变过程, ...
- css3选择器——导图篇
css3选择器主要有:基本选择器 , 层次选择器, 伪类选择器 , 伪元素选择器 , 属性选择器 基本选择器 层次选择器 伪类选择器分为 动态伪类选择器, 目标伪类选择器, 语言伪类选择器, U ...
- js构造函数,索引数组和属性的属性
本文主要介绍和小结js的构造函数,关联数组的实现方式和使用,及不可变对象和它的实现方式及他们使用过程中要注意的点 <script> function p(){ var len=argume ...
- iphone/ipad关于size, frame and bounds总结和UIScroll view学习笔记
1. iphone/ipad大小 Device Screen dimensions(in points) iphone and ipod 320 X 480 ipad 768 X 1024 2. UI ...
- unix的策略与机制
策略同机制分离,接口同引擎分离 Linux/Unix设计理念提供的一种机制不是策略.如果说机制是一种框架,那么,策略就是填充框架的一个个具体实施.机制提供的就是一种开放而宽松的环境,而策略就是在这个环 ...