Cod sursa(job #2778521)

Utilizator Edyci123Bicu Codrut Eduard Edyci123 Data 1 octombrie 2021 16:46:54
Problema Team Scor 100
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.55 kb
#include <bits/stdc++.h>
#define PII pair <int, int>
#define INF 0x3f3f3f3f
#define NMAX 505
#define PMAX 55

using namespace std;

class InParser
{
    #pragma warning(disable:4996)
    private:
        FILE* f;
        char* buff;
        int sp;
        char read()
        {
            ++sp;
            if (sp == 4096)
            {
                sp = 0;
                fread(buff, 1, 4096, f);
            }
            return buff[sp];
        }
    public:
        InParser(const char* nume)
        {
            sp = 4095;
            buff = new char[4096];
            f = fopen(nume, "r");
        }
        InParser& operator >> (int& n)
        {
            char c;
            while(!isdigit(c = read()));
                n = c - '0';
            while(isdigit(c = read()))
                n = n * 10 + c - '0';
            return *this;
        }
};

InParser f("team.in");
ofstream g("team.out");

int p, n, m, dp[PMAX][PMAX][PMAX], dest[PMAX], dist[NMAX], d[PMAX][PMAX];
vector <PII> edges[NMAX];
priority_queue <PII, vector <PII>, greater <PII>> pq;

void dijkstra(int nod)
{
    for(int i = 1; i <= n; i++)
        dist[i] = INF;
    dist[nod] = 0;
    pq.push(make_pair(0, nod));
    while(!pq.empty())
    {
        PII nod = pq.top();
        pq.pop();

        if(nod.first != dist[nod.second])
            continue;

        for(auto child : edges[nod.second])
            if(dist[child.first] > nod.first + child.second)
            {
                dist[child.first] = nod.first + child.second;
                pq.push(make_pair(dist[child.first], child.first));
            }
    }
}

int query(int st, int dr, int home)
{
    if(st > dr)
        return 0;

    if(dp[st][dr][home] != 0)
        return dp[st][dr][home];

    if(st == dr && dr == home)
        return 0;

    dp[st][dr][home] = INF;

    for(int i = st; i <= dr; i++)
        dp[st][dr][home] = min(dp[st][dr][home], query(st, i - 1, i) + query(i + 1, dr, i) + d[home][i]);
    return dp[st][dr][home];
}

int main()
{
    f >> p >> n >> m;

    for(int i = 1; i <= m; i++)
    {
        int x, y, cost;
        f >> x >> y >> cost;
        edges[x].push_back(make_pair(y, cost));
        edges[y].push_back(make_pair(x, cost));
    }

    dest[0] = 1;
    for(int i = 1; i <= p; i++)
        f >> dest[i];

    for(int i = 0; i <= p; i++)
    {
        dijkstra(dest[i]);
        for(int j = 0; j <= p; j++)
            d[i][j] = dist[dest[j]];
    }

    g << query(1, p, 0);


    return 0;
}