Cod sursa(job #2696101)

Utilizator Harsa_AndreiHarsa Andrei Harsa_Andrei Data 15 ianuarie 2021 12:37:21
Problema Cuplaj maxim de cost minim Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.43 kb
#include <fstream>
#include <vector>
#include <queue>

using namespace std;

ifstream cin("cmcm.in");
ofstream cout("cmcm.out");

const int NMAX = 300;
const int EMAX = 50000;
const int INF = 20000 * 5;

int N, M, E, S, D;
pair <int, int> edges[EMAX + 5];

vector <int> g[2 * NMAX + 5];
int cap[2 * NMAX + 5][2 * NMAX + 5], cost[2 * NMAX + 5][2 * NMAX + 5], flow[2 * NMAX + 5][2 * NMAX + 5];
int flowTo[2 * NMAX + 5], costTo[2 * NMAX + 5], bef[2 * NMAX + 5];
bool inQ[2 * NMAX + 5];

bool Bellman()
{
    for(int i = S; i <= D; i++)
    {
        flowTo[i] = costTo[i] = INF;
        inQ[i] = false;
    }

    queue <int> Q;
    Q.push(S);
    costTo[S] = 0;
    inQ[S] = true;

    while(!Q.empty())
    {
        int node = Q.front();
        Q.pop();
        inQ[node] = false;

        for(auto it : g[node])
            if(flow[node][it] < cap[node][it] && costTo[it] > costTo[node] + cost[node][it])
            {
                costTo[it] = costTo[node] + cost[node][it];
                flowTo[it] = min(flowTo[node], cap[node][it] - flow[node][it]);
                bef[it] = node;

                if(!inQ[it])
                {
                    inQ[it] = true;
                    Q.push(it);
                }
            }
    }

    return (costTo[D] != INF);
}

int main()
{
    cin >> N >> M >> E;

    S = 0, D = N + M + 1;
    for(int i = 1; i <= N; i++)
    {
        g[S].push_back(i);
        g[i].push_back(S);

        cap[S][i] = 1;
    }

    for(int i = 1; i <= M; i++)
    {
        g[N + i].push_back(D);
        g[D].push_back(N + i);

        cap[N + i][D] = 1;
    }

    for(int i = 1; i <= E; i++)
    {
        int x, y, c;
        cin >> x >> y >> c;

        g[x].push_back(N + y);
        g[N + y].push_back(x);
        edges[i] = {x, y};

        cap[x][N + y] = 1;

        cost[x][N + y] = c;
        cost[N + y][x] = -c;
    }

    int maxFlo = 0, minCost = 0;

    while(Bellman())
    {

        for(int node = D; node != S; node = bef[node])
        {
            flow[bef[node]][node] += flowTo[D];
            flow[node][bef[node]] -= flowTo[D];
        }

        maxFlo += flowTo[D];
        minCost += flowTo[D] * costTo[D];
    }

    cout << maxFlo << ' ' << minCost << '\n';
    for(int i = 1; i <= E; i++)
        if(flow[edges[i].first][N + edges[i].second] == 1)
            cout << i << ' ';

    return 0;
}