Cod sursa(job #1984164)

Utilizator borcanirobertBorcani Robert borcanirobert Data 23 mai 2017 21:26:19
Problema Flux maxim de cost minim Scor 70
Compilator cpp Status done
Runda Arhiva educationala Marime 1.95 kb
#include <iostream>
#include <fstream>
#include <cstring>
#include <vector>
#include <queue>
using namespace std;

ifstream fin("fmcm.in");
ofstream fout("fmcm.out");

const int MAXN = 355;
const int Inf = 0x3f3f3f3f;
struct Nod{
	int cost, nod;

	bool operator < ( const Nod& a ) const
	{
		return cost > a.cost;
	}
};
int N, M, S, D;
vector< vector<int> > G;
int F[MAXN][MAXN];
int m[MAXN][MAXN];
int c[MAXN];
int t[MAXN];
int RealCost[MAXN];
int P[MAXN];
int cmin;

void Read();
void Bellman_Ford();
bool Dijkstra();

int main()
{
	Read();
	Bellman_Ford();

	while ( Dijkstra() );

	fout << cmin << '\n';

	fin.close();
	fout.close();
	return 0;
}


void Read()
{
	fin >> N >> M >> S >> D;
	G = vector< vector<int> >(N + 1);
	int x, y, c, z;
	while ( M-- )
	{
		fin >> x >> y >> c >> z;

		G[x].push_back(y);
		G[y].push_back(x);

		F[x][y] = c;

		m[x][y] = z;
		m[y][x] = -z;
	}
}

void Bellman_Ford()
{
	queue<int> Q;

	P[S] = 0;
	Q.push(S);

	while ( !Q.empty() )
	{
		int node = Q.front();
		Q.pop();

		for ( const int& v : G[node] )
		{
			//cout << node << ' ' << v; cin.get();
			if ( P[v] > P[node] + 1 )
			{
				//cout << v; cin.get();
				P[v] = P[node] + 1;
				Q.push(v);
			}
		}
	}
}

bool Dijkstra()
{
	memset(c, Inf, sizeof(c));
	c[S] = RealCost[S] = 0;
	priority_queue<Nod> Q;
	Q.push({0, S});

	while ( !Q.empty() )
	{
		int node = Q.top().nod;
		int cc = Q.top().cost;
		Q.pop();

		if ( cc != c[node] ) continue;
		for ( const int& v : G[node] )
			if ( F[node][v] )
			{
				int c_nou = c[node] + P[node] - P[v] + m[node][v];

				if ( c_nou < c[v] )
				{
					c[v] = c_nou;
					RealCost[v] = RealCost[node] + m[node][v];
					t[v] = node;

					Q.push({c[v], v});
				}
			}
	}
	for ( int i = 1; i <= N; ++i )
		P[i] = c[i];

	if ( c[D] >= Inf )
		return false;

	int fc{Inf};
	for ( int i = D; i != S; i = t[i] )
		fc = min( F[t[i]][i], fc );

	cmin += fc*RealCost[D];

	for ( int i = D; i != S; i = t[i] )
	{
		F[t[i]][i] -= fc;
		F[i][t[i]] += fc;
	}

	return true;
}