POJ1459《Power Network》方法:Dinic

采用先分层,再用DFS找增广路的的方法。O(n^2m)

#include <iostream>
#include <queue>

using namespace std;
#define min(a,b) (a<b?a:b)
#define MAXN 105
const int inf = 0x7fffffff;

struct {
	int flow;
	int capacity;
} map[MAXN][MAXN];

int n, np, nc, m; //n节点总数,np发电站数,nc消费者数,m边数
int maxflow, sp, fp; //最大流,源点,汇点
int depth[MAXN]; // 用于dinic分层

bool bfs() //分层
{
	memset(depth, 0, sizeof(depth));
	int u;
	queue<int> q;
	q.push(sp);
	depth[sp] = 1;
	while (!q.empty()) {
		u = q.front(); q.pop();
		for (int v = 1; v <= n; ++v) {
			if (!depth[v] && map[u][v].capacity > map[u][v].flow) {
				q.push(v);
				depth[v] = depth[u] + 1;
			}
		}
		if (u == fp)
			return true;
	}
	return false;
}

int dfs(int cur, int sum)
{
	if (cur == fp)
		return sum;
	int s = sum, ret;
	for (int v = 1; v <= n; ++v) { //只跟上下层有关,牛
		if (depth[v] == depth[cur]+1 && s && map[cur][v].capacity > map[cur][v].flow) {
			ret = dfs(v, min(map[cur][v].capacity - map[cur][v].flow, s));
			map[cur][v].flow += ret;
			map[v][cur].flow -= ret;
			s -= ret;
		}
	}
	return sum - s;
}

void dinic()
{
	maxflow = 0;
	while (bfs())
		maxflow += dfs(sp, inf);
}

int main()
{
	//freopen("temp.txt", "r", stdin);
	int x, y, z;
	char tmp;
	while (cin >> n >> np >> nc >> m) {
		memset(map, 0, sizeof(map));
		
		for (int i = 1; i <= m; ++i) {
			cin >> tmp >> x >> tmp >> y >> tmp >> z;
			map[x+1][y+1].capacity = z;
		}
		//新建源点指向所有的发电站
		sp = n+1;
		fp = n+2;
		n += 2;
		for (int i = 1; i <= np; ++i) {
			cin >> tmp >> x >> tmp >> y;
			map[sp][x+1].capacity = y;
		}
		//新建汇点,使所有消费者指向它
		for (int i = 1; i <= nc; ++i) {
			cin >> tmp >> x >> tmp >> y;
			map[x+1][fp].capacity = y;
		}

		dinic();
		cout << maxflow << endl;
	}
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值