Cod sursa(job #501060)

Utilizator tamas_iuliaTamas Iulia tamas_iulia Data 14 noiembrie 2010 11:43:40
Problema Team Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.8 kb
#include <stdio.h>
#include <string.h>
#include <vector>
#include <queue>
#define Nmax 502
#define Pmax 52
#define mp make_pair
#define pb push_back
#define y first
#define c second
#define INF 0x3f3f3f3f

using namespace std;

queue< int > Q;
vector< pair<int,int> >v[Nmax];
int dist[Pmax][Pmax],daux[Nmax],dest[Pmax];
bool use[Nmax];
int a[Pmax][Pmax][Pmax];
int N,M,P;

inline int Minim(int x,int y){ return x<y ? x:y; }
void bellman_ford(int wh){
    int i,x;
    vector< pair<int,int> >:: iterator it;
    memset(use,0,sizeof(use));
    for(i=1;i<=N;++i) daux[i]=INF;
    daux[dest[wh]]=0; use[dest[wh]]=1;
    Q.push(dest[wh]);

    while(!Q.empty() ){
        x=Q.front(); Q.pop();
        use[x]=0;

        for(it=v[x].begin(); it!=v[x].end(); ++it)
            if( daux[it->y] > daux[x]+it->c ){
                daux[it->y] = daux[x]+it->c;
                if( ! use[it->y] ){
                    use[it->y]=1;
                    Q.push(it->y);
                }
            }
    }
    for(i=0;i<=P;++i) dist[wh][i]=daux[dest[i]];
}

inline int Din(int i,int j,int k){
    int u;
    if( i>j ) return 0;
    if( a[i][j][k] != INF ) return a[i][j][k];

    for(u=i;u<=j;++u)
        a[i][j][k]=Minim(a[i][j][k], Din(i,u-1,u)+Din(u+1,j,u)+dist[k][u]);
    return a[i][j][k];
}

int main(){
    int i,x,y,z,rez;
    freopen("team.in","r",stdin);
    freopen("team.out","w",stdout);
    scanf("%d%d%d",&P,&N,&M);
    for(i=1;i<=M;++i){
        scanf("%d%d%d",&x,&y,&z);
        v[x].pb(mp(y,z));
        v[y].pb(mp(x,z));
    }
    for(i=1;i<=P;++i)scanf("%d",&dest[i]);
    dest[0]=1;

    for(i=0;i<=P;++i)
        bellman_ford(i);

    memset(a,INF,sizeof(a));
    rez=Din(1,P,0);
    printf("%d\n",rez);
    fclose(stdin); fclose(stdout);
    return 0;
}