Cod sursa(job #867992)

Utilizator fhandreiAndrei Hareza fhandrei Data 30 ianuarie 2013 15:36:59
Problema Flux maxim de cost minim Scor 50
Compilator cpp Status done
Runda Arhiva educationala Marime 2.07 kb
// Include
#include <fstream>
#include <algorithm>
#include <vector>
#include <utility>
#include <queue>
using namespace std;

// Definitii
#define pb push_back
#define mp make_pair

#define edge pair<int, int>
#define edgeCost first
#define edgeNode second

// Constante
const int sz = 351;
const int oo = (1<<30)-1;

// Functii
bool dijkstra();

// Variabile
ifstream in("fmcm.in");
ofstream out("fmcm.out");

int nodes, edges, source, destination;
int maxFlowMinCost;
int father[sz], dist[sz];
int cost[sz][sz], capacity[sz][sz], flow[sz][sz];

vector<int> graph[sz];

// Main
int main()
{
	in >> nodes >> edges >> source >> destination;
	
	int rFrom, rTo, rCapacity, rCost;
	while(edges--)
	{
		in >> rFrom >> rTo >> rCapacity >> rCost;
		graph[rFrom].pb(rTo);
		graph[rTo].pb(rFrom);
		
		cost[rFrom][rTo] = rCost;
		cost[rTo][rFrom] = -rCost;
		capacity[rFrom][rTo] = rCapacity;
	}
	
	while(dijkstra())
	{
		int minFlow = oo;
		
		for(int node=destination ; node!=source ; node=father[node])
			minFlow = min(minFlow, capacity[father[node]][node] - flow[father[node]][node]);
		
		for(int node=destination ; node!=source ; node=father[node])
		{
			flow[father[node]][node] += minFlow;
			flow[node][father[node]] -= minFlow;
		}
		
		maxFlowMinCost += minFlow*dist[destination];
	}
	
	out << maxFlowMinCost;
	
	in.close();
	out.close();
	return 0;
}

bool dijkstra()
{
	for(int i=1 ; i<=nodes ; ++i)
	{
		dist[i] = oo;
		father[i] = 0;
	}
	
	priority_queue<edge, vector<edge>, greater<edge> > heap;
	
	dist[source] = 0;
	heap.push(mp(0, source));
	
	while(!heap.empty())
	{
		int current = heap.top().edgeNode;
		heap.pop();
		vector<int>::iterator it, end = graph[current].end();
		for(it=graph[current].begin() ; it!=end ; ++it)
		{
			if(capacity[current][*it] != flow[current][*it]   &&   dist[current]+cost[current][*it] < dist[*it])
			{
				father[*it] = current;
				dist[*it] = dist[current]+cost[current][*it];
				heap.push(mp(dist[*it], *it));
			}
		}
	}
	return father[destination]? 1:0;
}