Cod sursa(job #3179087)

Utilizator xDemonstyMatei Haba Ionut xDemonsty Data 2 decembrie 2023 23:26:53
Problema Ubuntzei Scor 75
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.27 kb
#include <fstream>
#include <vector>
#include <queue>
using namespace std;
ifstream cin("ubuntzei.in");
ofstream cout("ubuntzei.out");

long long n, m, k ;

vector<pair<long long, long long >> ubunt [ 30 ];
vector<pair<long long,long long >> graf [ 2005 ];

long long unde [ 30 ];
long long dp [ 30 ] [ 135000 ];
long long frv[ 31 ] ;
int main()
{

    cin >> n >> m ;
    cin >> k ;


    for ( int i = 2; i <= k + 1; i ++ )
    {
        cin >> unde [ i ] ;
        frv[ unde [ i ] ] = i ;
    }

    unde [1 ] = 1;
    frv[ 1 ] = 1;
    unde [ k + 2] = n ;

    frv[ n ] = k + 2 ;
    for ( int i = 1; i <= m ; i ++ )
    {
        long long a, b,c ;
        cin >> a >> b >> c ;
        graf[a ] .push_back({b,c});
        graf[ b ] .push_back({a,c});
    }


    for (int i = 1 ; i <= k + 2; i ++  )
    {

        priority_queue<pair<long long,long long>> pq ;
        vector<long long> dp ( n + 1, 1e18 );

        dp[ unde [ i ]] = 0 ;
        pq.push({dp [ unde [i ] ], unde [ i ] } ) ;

        while ( !pq.empty() )
        {
            long long nod = pq.top().second ;

            if( frv [ nod ] != 0 )
            {
                ubunt [ i ] .push_back( {frv [ nod ], dp [ nod ]} ) ;
            }
            pq.pop();
            for ( int j = 0 ; j < graf[ nod ].size() ; j ++ )
            {
                long long u = graf[ nod ] [ j ].first ;

                if( dp [ u ] > dp [ nod ] + graf[ nod ] [ j ] .second )
                {
                    dp [ u ] = dp [ nod ] + graf[ nod ] [ j ] .second;
                    pq.push({-dp[u],u });

                }
            }
        }

    }
    /*for ( int i = 0 ; i < ubunt [  1 ] .size() ; i ++ )
    {
        cout << ubunt [ 1 ] [ i ].first << " " << ubunt [ 1 ] [ i ] .second << '\n';
    }


    return 0 ;*/
    queue<pair<long long,pair<long long,long long>>> pq ; // cost , pozitie , masca

    dp [ 1 ][ 1 ] = 0 ;
    pq.push({0, {1, 1}} );

    long long sol =0;
    for (int j = 0 ; j < k + 2; j ++ )
        sol += ( 1 << j ) ;

    //cout << sol << '\n';
    while ( !pq.empty() )
    {
        long long a = pq.front().first;
        long long b = pq.front().second.first;
        long long mask = pq.front().second .second ;
        pq.pop();
        //cout << b << " " << mask << '\n';
        for ( int i = 0 ; i < ubunt  [ b ] .size() ; i ++ )
        {
            long long nod = ubunt [ b ] [ i ] .first ;
            long long cst = ubunt [ b ] [ i ] . second ;

            long long val = ( 1 << (nod - 1) );
            long long tal = mask & val ;
            //cout << nod << " " << tal << '\n';
            if ( tal == 0  )
            {


                long long cal = mask ^ (1<<(nod -1)) ;

                /*if ( b == 2 && nod == 3 )
                {
                    cout << mask << " " << nod << '\n';
                }*/
                if ( dp [ nod ] [ cal  ] > dp [b] [ mask ] + cst || dp[ nod  ][ cal ] == 0 )
                {
                    dp [ nod ] [ cal  ] = dp [ b ] [ mask ] + cst;
                    pq.push({-dp [ nod ] [ cal ], {nod, cal }} );

                }
            }
        }

    }
    //cout << sol << '\n';
    cout << dp [ k + 2 ] [ sol  ] ;
    return 0;
}