标签:
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <cstdlib>
#include <queue>
using namespace std;
typedef long long ll;
const int OF = 100;
const int INF = 0x3f3f3f3f;
const int N = 500;
int n, m, G[N][N], f[N][N];
void Input() { //把一开始的N个regulator(调节器)拆成两个点一条路
memset(G, 0, sizeof(G));
memset(f, 0, sizeof(f));
int num;
for (int i = 1; i <= n; i++) {
scanf("%d", &num);
G[i + OF][i] = num;
}
scanf("%d", &m);
int a, b, c;
for (int i = 0; i < m; i++) {
scanf("%d %d %d", &a, &b, &c);
G[a][b + OF] = c;
}
scanf("%d %d", &a, &b);
for (int i = 0; i < a; i++) { //增加超级源点
scanf("%d", &c);
G[0][c + OF] = INF;
}
for (int i = 0; i < b; i++) { //增加超级汇点
scanf("%d", &c);
G[c][n + OF + 1] = INF;
}
}
int EK() {
queue<int> Q;
n = n + OF + 1;
int pre[N], a[N], ans = 0;
memset(f, 0, sizeof(f));
while (1) {
memset(pre, 0, sizeof(pre));
memset(a, 0, sizeof(a));
a[0] = INF;
Q.push(0);
while (!Q.empty()) { //BFS找增广路
int u = Q.front(); Q.pop();
for (int v = 0; v <= n; v++) {
if (!a[v] && G[u][v] > f[u][v]) { //找到新结点
pre[v] = u; //记录新节点的父亲
Q.push(v); //加入FIFO队列
a[v] = min(a[u], G[u][v] - f[u][v]); //s - t的最小残量
}
}
}
if (a[n] == 0) break; //当找不到新的增广路时,就已是最大流
ans += a[n]; //更新从s流出的总流量
for (int u = n; u != 0; u = pre[u]) { //从源点s往回走
f[pre[u]][u] += a[n]; //更新正向边
f[u][pre[u]] -= a[n]; //更新反向边
}
}
return ans;
}
int main() {
while (scanf("%d", &n) != EOF) {
Input(); //读入数据,拆点
printf("%d\n", EK());
}
return 0;
}
版权声明:本文为博主原创文章,未经博主允许不得转载。
uva 10330 Power Transmission (最大流 + 拆点)
标签:
原文地址:http://blog.csdn.net/llx523113241/article/details/46889163