Cod sursa(job #3350908)

Utilizator DobraVictorDobra Victor Ioan DobraVictor Data 14 aprilie 2026 18:50:44
Problema Flux maxim Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.5 kb
#include <iostream>
#include <fstream>
#include <stdint.h>

const int32_t MAX_N = 1000;
const int32_t MAX_M = 5000;
const int32_t MAX_FLOW = 1000000000;

int32_t min(int32_t x, int32_t y) {
	return (x < y) ? x : y;
}

struct Node {
	int32_t adjStart, adjInd;
	int32_t level;
};
struct AdjItem {
	int32_t node, flow, cap;
	int32_t next;
};

int32_t n, m;
Node nodes[MAX_N];
AdjItem adj[MAX_M << 1];
int32_t queue[MAX_N];

void ReadGraph(std::istream& fin) {
	fin >> n >> m;

	for(int32_t i = 0; i != n; ++i)
		nodes[i].adjStart = -1;
	for(int32_t i = 0; i != m; ++i) {
		int32_t node1, node2, cap;
		fin >> node1 >> node2 >> cap;
		--node1; --node2;

		adj[i << 1].node = node2;
		adj[i << 1].flow = 0;
		adj[i << 1].cap = cap;
		adj[i << 1].next = nodes[node1].adjStart;
		nodes[node1].adjStart = i << 1;

		adj[(i << 1) + 1].node = node1;
		adj[(i << 1) + 1].flow = 0;
		adj[(i << 1) + 1].cap = 0;
		adj[(i << 1) + 1].next = nodes[node2].adjStart;
		nodes[node2].adjStart = (i << 1) + 1;
	}
}
bool BuildGraphLevels() {
	for(int32_t i = 0; i != n; ++i) {
		nodes[i].adjInd = nodes[i].adjStart;
		nodes[i].level = -1;
	}

	queue[0] = 0;
	nodes[0].level = 0;

	for(int32_t start = 0, end = 1; start != end; ++start) {
		int32_t node = queue[start];

		for(int32_t ind = nodes[node].adjStart; ind != -1; ind = adj[ind].next) {
			int32_t next = adj[ind].node;
			if(nodes[next].level != -1 || adj[ind].flow == adj[ind].cap)
				continue;
			
			nodes[next].level = nodes[node].level + 1;
			queue[end++] = next;
		}
	}

	return nodes[n - 1].level != -1;
}
int32_t DFSExtractFlow(int32_t node, int32_t flow) {
	if(node == n - 1 || !flow)
		return flow;
	
	for(int32_t& ind = nodes[node].adjInd; ind != -1; ind = adj[ind].next) {
		int32_t next = adj[ind].node;
		if(nodes[next].level != nodes[node].level + 1)
			continue;
		
		int32_t nextFlow = min(flow, adj[ind].cap - adj[ind].flow);
		int32_t resFlow = DFSExtractFlow(next, nextFlow);

		if(resFlow) {
			adj[ind].flow += resFlow;
			adj[ind ^ 1].flow -= resFlow;
			return resFlow;
		}
	}

	return 0;
}
int32_t CalcMaxFlow() {
	int32_t maxFlow = 0;

	while(BuildGraphLevels()) {
		int32_t currFlow;
		do {
			currFlow = DFSExtractFlow(0, MAX_FLOW);
			maxFlow += currFlow;
		} while(currFlow);
	}

	return maxFlow;
}

int main() {
	std::ifstream fin("maxflow.in");
	std::ofstream fout("maxflow.out");

	ReadGraph(fin);
	fout << CalcMaxFlow() << '\n';

	fin.close();
	fout.close();

	return 0;
}