Cod sursa(job #1217831)

Utilizator pulseOvidiu Giorgi pulse Data 8 august 2014 13:41:47
Problema Flux maxim de cost minim Scor 50
Compilator cpp Status done
Runda Arhiva educationala Marime 2.33 kb
#include <cstdio>
#include <queue>
#include <cstring>
#include <vector>
#define INF 0x3f3f3f3f

using namespace std;

const int MAXN = 355;
int N, M, S, D;
int C[MAXN][MAXN], Cst[MAXN][MAXN];
int F, FCst;
vector <int> G[MAXN];
int old_d[MAXN], d[MAXN], real_d[MAXN], T[MAXN];
char inQ[MAXN];
queue <int> Q;
//priority_queue < pair <int, int>, vector < pair <int, int> >, greater < pair<int, int> > > H;
priority_queue < pair <int, int> > H;

bool Dijkstra()
{
	memset(d, 0x3f, sizeof(d));
	d[S] = 0; real_d[S] = 0;
	H.push(make_pair(d[S], S));
	for (; !H.empty(); )
	{
		int cst = H.top().first;
		int node = H.top().second;
		H.pop();
		if (d[node] != cst) continue;
		for (vector <int> :: iterator it = G[node].begin(); it != G[node].end(); ++it)
		{
			int V = *it;
			if (C[node][V])
			{
				int new_d = d[node] + Cst[node][V] + old_d[node] - old_d[V];
				if (new_d < d[V])
				{
					d[V] = new_d;
					real_d[V] = real_d[node] + Cst[node][V];
					T[V] = node;
					H.push(make_pair(d[V], V));
				}
			}
		}
	}
	memcpy(old_d, real_d, sizeof(d));
	if (d[D] == INF) return false;
	int Min = INF, currCst = 0;
	for (int node = D; node != S; node = T[node])
		Min = min(Min, C[T[node]][node]),
		currCst += Cst[T[node]][node];
	F += Min;
	FCst += Min * real_d[D];
	for (int node = D; node != S; node = T[node])
		C[T[node]][node] -= Min,
		C[node][T[node]] += Min;
	return true;
}

bool Bellman_Ford()
{
	memset(old_d, 0x3f, sizeof(old_d));
	old_d[S] = 0;
	for (Q.push(S), inQ[S] = 1; !Q.empty(); Q.pop())
	{
		int node = Q.front();
		inQ[node] = 0;
		for (vector <int> :: iterator it = G[node].begin(); it != G[node].end(); ++it)
		{
			int V = *it;
			if (C[node][V])
			{
				if (old_d[V] <= old_d[node] + Cst[node][V]) continue;
				old_d[V] = old_d[node] + Cst[node][V];
				if (inQ[V]) continue;
				Q.push(V);
				inQ[V] = 1;
			}
		}
	}
	if (old_d[D] == INF) return false;
	return true;
}

int main()
{
	freopen("fmcm.in", "r", stdin);
	freopen("fmcm.out", "w", stdout);
	scanf("%d %d %d %d", &N, &M, &S, &D);
	for (int i = 1; i <= M; ++i)
	{
		int a, b;
		scanf("%d %d", &a, &b);
		G[a].push_back(b);
		G[b].push_back(a);
		scanf("%d %d", &C[a][b], &Cst[a][b]);
		Cst[b][a] = -Cst[a][b];
	}
	Bellman_Ford();
	for (; Dijkstra(); );
	printf("%d\n", FCst);
	return 0;
}