您的位置:首页 > 产品设计 > UI/UE

uva 10746 - Crime Wave - The Sequel(费用流)

2013-11-22 20:55 411 查看
题目链接:uva 10746 - Crime Wave - The Sequel

题目大意:自从银行被抢之后,警局为每个银行都安排了一个警察,现在有n个银行和m警察,给出每个警察到达各个银行的时间,问说怎么样安排人手,可以使的警察到达银行的平均时间最小。

解题思路:网络流的最小费用最大流,起点s与m个警察相连,容量为1,费用为0;n个银行与汇点t相连,容量为1,费用为0;然后就是警察和银行之间的边,为有向边,警察指向银行,费用为时间。然后建好图就是单纯的费用流问题。

#include <stdio.h>
#include <string.h>
#include <math.h>
#include <queue>
#include <vector>

using namespace std;

#define min(a,b) (a)<(b)?(a):(b)

const int N = 205;
const int T = 100;
const int INF = 1 << 30;

int n, m, tmp, g

, f

;
double cost

;
vector<int> v
;

void add(int x,  int y) {
g[x][y]++;
v[x].push_back(y);
v[y].push_back(x);
}

void init() {

tmp = 200;
memset(g, 0, sizeof(g));
memset(f, 0, sizeof(f));
memset(cost, 0, sizeof(cost));
for (int i = 0; i < N; i++)
v[i].clear();

for (int i = 1; i <= n; i++) {

add(0, i + T);
add(i + T, i);
for (int j = 1; j <= m; j++) {
add(i, j + n + T);
}
}

for (int i = 1; i <= m; i++) {
add(i + n + T, i + n);
add(i + n, tmp);
}

for (int i = 1; i <= n; i++) {
for (int j = 1; j <= m; j++) {
scanf("%lf", &cost[i][j + n + T]);
cost[j + n + T][i] = -cost[i][j + n + T];
}
}
}

void solve() {
queue<int> que;
double ans = 0, d
;
int c, flow = 0,  path
, vis
;

while (1) {

for (int i = 0; i <= tmp; i++)
d[i] = (i == 0) ? 0 : INF;
memset(path, 0, sizeof(path));
memset(vis, 0, sizeof(vis));
que.push(0);
vis[0] = 1;

while (!que.empty() ) {
c = que.front(), que.pop();
vis[c] = 0;

int top = v[c].size();
for (int i = 0; i < top; i++) {
if (g[c][v[c][i]] > f[c][v[c][i]] && d[v[c][i]] - d[c] - cost[c][v[c][i]] > 1e-6) {
d[v[c][i]] = d[c] + cost[c][v[c][i]];
path[v[c][i]] = c;

if ( vis[v[c][i]] == 0) {
que.push(v[c][i]);
vis[v[c][i]] = 1;
}
}
}
}

if (INF - d[tmp] < 1e-6) break;
int t = INF;

for (int i = tmp; i; i = path[i]) t = min(g[path[i]][i] - f[path[i]][i], t);

flow += t;
ans += t * d[tmp];

for (int i = tmp; i; i= path[i]) {
f[path[i]][i] += t;
f[i][path[i]] -= t;
}
}
printf("%.2lf\n", ans / n + 0.001);
}

int main () {
while (scanf("%d%d", &n, &m), n + m) {
init();
solve();
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: