Pagini recente » Cod sursa (job #394932) | Cod sursa (job #18731) | Cod sursa (job #2712967) | Cod sursa (job #3253933) | Cod sursa (job #2978484)
#include <bits/stdc++.h>
#define MAX_N 300
#define MAX_M 300
#define MAX_VT (MAX_N + MAX_M + 2)
#define MULT (1 << 30)
using namespace std;
int muchie[MAX_VT + 1][MAX_VT + 1];
struct FLOW {
struct elemPQ {
int u, cost;
bool operator < (const elemPQ& a) const {
return cost > a.cost;
}
};
int s, t, vt;
int maxFlow, minCost;
bool inQ[MAX_VT], vis[MAX_VT];
int cap[MAX_VT][MAX_VT], cost[MAX_VT][MAX_VT], flux[MAX_VT][MAX_VT], parent[MAX_VT], realCost[MAX_VT], newCost[MAX_VT], fakeCost[MAX_VT];
vector <int> edges[MAX_VT];
void add_edge(int u, int v, int c, int z) {
edges[u].push_back(v);
edges[v].push_back(u);
cap[u][v] = c;
cost[u][v] = z;
cost[v][u] = -z;
}
void bellman() {
int u;
queue <int> q;
for (u = 0; u < vt; u++)
newCost[u] = MULT;
for (u = 0; u < vt; u++)
inQ[u] = false;
newCost[s] = 0;
q.push(s);
while (!q.empty()) {
u = q.front();
q.pop();
inQ[u] = false;
for (int v : edges[u]) {
if (newCost[u] + cost[u][v] < newCost[v] && flux[u][v] < cap[u][v]) {
parent[v] = u;
newCost[v] = newCost[u] + cost[u][v];
if (!inQ[v]) {
q.push(v);
inQ[v] = true;
}
}
}
}
}
bool dijkstra() {
int u;
priority_queue <elemPQ> pq;
for (u = 0; u < vt; u++) {
parent[u] = -1;
realCost[u] = newCost[u];
fakeCost[u] = MULT;
vis[u] = false;
}
newCost[s] = fakeCost[s] = 0;
pq.push({ s, 0 });
while (!pq.empty()) {
u = pq.top().u;
pq.pop();
if (!vis[u]) {
vis[u] = true;
for (int v : edges[u]) {
if (fakeCost[u] + cost[u][v] + realCost[u] - realCost[v] < fakeCost[v] && flux[u][v] < cap[u][v]) {
parent[v] = u;
fakeCost[v] = fakeCost[u] + cost[u][v] + realCost[u] - realCost[v];
newCost[v] = newCost[u] + cost[u][v];
pq.push({ v, fakeCost[v] });
}
}
}
}
return fakeCost[t] != MULT;
}
void minCostmaxFlow() {
int newFlow, newCost, v;
bellman();
maxFlow = 0;
minCost = 0;
while (dijkstra()) {
newFlow = MULT;
newCost = 0;
v = t;
while (v != s) {
newFlow = min(newFlow, cap[parent[v]][v] - flux[parent[v]][v]);
newCost += cost[parent[v]][v];
v = parent[v];
}
maxFlow += newFlow;
minCost += newFlow * newCost;
v = t;
while (v != s) {
flux[parent[v]][v] += newFlow;
flux[v][parent[v]] -= newFlow;
v = parent[v];
}
}
}
};
FLOW cuplaj;
int main() {
ifstream cin("cmcm.in");
ofstream cout("cmcm.out");
int n, m, k, u, v, c;
cin >> n >> m >> k;
for (int i = 1; i <= k; i++) {
cin >> u >> v >> c;
v += n;
muchie[u][v] = i;
cuplaj.add_edge(u, v, 1, c);
}
for (u = 1; u <= n; u++)
cuplaj.add_edge(0, u, 1, 0);
for (v = n + 1; v <= n + m; v++)
cuplaj.add_edge(v, n + m + 1, 1, 0);
cuplaj.s = 0;
cuplaj.t = n + m + 1;
cuplaj.vt = n + m + 2;
cuplaj.minCostmaxFlow();
cout << cuplaj.maxFlow << " " << cuplaj.minCost << "\n";
for (u = 1; u <= n; u++) {
for (v = n + 1; v <= n + m; v++) {
if (cuplaj.flux[u][v])
cout << muchie[u][v] << " ";
}
}
return 0;
}