Pagini recente » Cod sursa (job #46) | Cod sursa (job #2279980) | Cod sursa (job #1146053) | Cod sursa (job #53751) | Cod sursa (job #3154429)
#include <bits/stdc++.h>
using namespace std;
const int NMAX = 351;
int n, m, source, sink;
int h[NMAX], real_h[NMAX], dist[NMAX], parent[NMAX], cap[NMAX][NMAX];
vector<vector<pair<int, int>>> g;
void bellman_ford(int start_node) {
fill(h+1, h+n+1, 1e9);
h[start_node] = 0;
for(int i = 0; i < n-1; i++) {
for(int node = 1; node <= n; node++) {
for(auto [son, w] : g[node])
if(cap[node][son] > 0 && h[node] + w < h[son])
h[son] = h[node] + w;
}
}
}
// Dijkstra
bool bfs(int start) {
priority_queue<pair<int, int>> pq;
pq.push({0, start});
fill(dist+1, dist+n+1, INT_MAX);
dist[start] = 0;
real_h[start] = 0;
while(!pq.empty()) {
int node = pq.top().second;
pq.pop();
for(auto [son, w] : g[node]) {
if(cap[node][son] <= 0 || dist[son] <= dist[node] + w + h[node] - h[son]) continue ;
dist[son] = dist[node] + w + h[node] - h[son];
real_h[son] = real_h[node] + w;
parent[son] = node;
pq.push({-dist[son], son});
}
}
return dist[sink] != INT_MAX;
}
int flow() {
int flow_cost = 0;
while(bfs(source)) {
int node = sink, curr_flow = INT_MAX;
while(node != source) {
curr_flow = min(curr_flow, cap[parent[node]][node]);
node = parent[node];
}
for(int i = 1; i <= n; i++) h[i] = real_h[i];
node = sink;
while(node != source) {
cap[node][parent[node]] += curr_flow;
cap[parent[node]][node] -= curr_flow;
node = parent[node];
}
flow_cost += curr_flow * h[sink] ;
}
return flow_cost;
}
int main() {
scanf("%d %d %d %d", &n, &m, &source, &sink);
g.resize(n+1);
for(int i = 0; i < m; i++) {
int x, y, c, w;
scanf("%d %d %d %d", &x, &y, &c, &w);
cap[x][y] = c;
g[x].push_back({y, w});
g[y].push_back({x, -w});
}
bellman_ford(source);
// for(int node = 1; node <= n; node++) printf("%d ", h[node]);
// puts("");
printf("%d\n", flow());
return 0;
}