Pagini recente » Cod sursa (job #1235997) | Cod sursa (job #3038734) | Cod sursa (job #236121) | Cod sursa (job #3282419) | Cod sursa (job #3191351)
#include <vector>
#include <iostream>
#include <fstream>
#include <climits>
#include <queue>
#include <unordered_map>
using namespace std;
ifstream fin("cc.in");
ofstream fout("cc.out");
vector<vector<int>> adj, dist;
vector<unordered_map<int, int>> capacity, flow;
int source, target, n;
vector<int> parent, minDist;
const int INF = INT_MAX;
int result = 0;
int bfs()
{
for (int i = 0; i <= target; i++)
{
parent[i] = -1;
minDist[i] = INF;
}
minDist[source] = 0;
queue<pair<int, int>> q;
q.push({source, INF});
while (!q.empty())
{
int currentNode = q.front().first;
int currentFlow = q.front().second;
q.pop();
for (auto &neigh : adj[currentNode])
{
if (minDist[neigh] > minDist[currentNode] + dist[currentNode][neigh] && capacity[currentNode][neigh] > flow[currentNode][neigh])
{
parent[neigh] = currentNode;
int residualFlow = capacity[currentNode][neigh] - flow[currentNode][neigh];
int bottleneck = min(currentFlow, residualFlow);
minDist[neigh] = minDist[currentNode] + dist[currentNode][neigh];
q.push({neigh, bottleneck});
}
}
}
return parent[target] >= 0;
}
void maxflow()
{
int newFlow;
parent.resize(target + 2);
while (true)
{
newFlow = bfs();
if (newFlow == 0)
break;
int currentNode = target;
while (currentNode != source)
{
int parentNode = parent[currentNode];
flow[parentNode][currentNode] += newFlow;
flow[currentNode][parentNode] -= newFlow;
currentNode = parentNode;
}
result += minDist[target];
}
}
void read()
{
fin >> n;
source = 0;
target = 2 * n + 1;
capacity.resize(target + 1);
flow.resize(target + 1);
adj.resize(target + 1);
dist.resize(target + 1, vector<int>(target + 1));
minDist.resize(target + 1);
int x, y;
for (int i = 1; i <= n; i++)
{
adj[source].push_back(i);
adj[i].push_back(source);
capacity[source][i] = 1;
for (int j = 1; j <= n; ++j)
{
fin >> y;
adj[i].push_back(j + n);
adj[j + n].push_back(i);
capacity[i][j + n] = 1;
dist[i][j + n] = y;
dist[j + n][i] = -y;
}
adj[i + n].push_back(target);
adj[target].push_back(i + n);
capacity[i + n][target] = 1;
}
}
int main()
{
read();
maxflow();
fout << result;
return 0;
}