Cod sursa(job #1129260)

Utilizator cernat.catallinFMI Cernat Catalin Stefan cernat.catallin Data 27 februarie 2014 21:01:38
Problema Ubuntzei Scor 70
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.89 kb
#include <stdio.h>
#include <vector>
#include <queue>
#include <algorithm>
using namespace std;

#define Nmax 2005
#define Kmax 16
#define inf 1073741824

vector < pair<int, int> > graph[Nmax];
int p[Kmax], dist[Nmax];
int edges[Kmax + 2][Kmax + 2];
int mat[1 << Kmax][Kmax];
int n, m, k;

struct cmp{
	bool operator() (const int &i, const int &j){
		return dist[i] < dist[j];
	}
};
priority_queue <int , vector <int>, cmp> heap;

inline int min(int a, int b){
	return (a < b) ? a : b;
}

void read(){
	freopen("ubuntzei.in", "r", stdin);
    int u, v, c;

	scanf("%d %d %d", &n, &m, &k);
	for (int i = 1; i <= k; ++i)
		scanf("%d", &p[i]);
	p[0] = 1;
	p[k + 1] = n;
	++k;
	for (int i = 1; i <= m; ++i){
		scanf("%d %d %d", &u, &v, &c);
		graph[u].push_back( make_pair(v, c) );
		graph[v].push_back( make_pair(u, c) );
	}
	fclose(stdin);
}

void dijkstra(int s){
	vector < pair <int, int> >::iterator it;
	int u;

	for (int i = 1; i <= n; ++i)
		dist[i] = inf;
	dist[s] = 0;
	heap.push(s);

	while ( !heap.empty() ){
		u = heap.top();
		heap.pop();

		for (it = graph[u].begin(); it != graph[u].end(); ++it)
			if (dist[it->first] > dist[u] + it->second){
				dist[it->first] = dist[u] + it->second;
				heap.push(it->first);
			}
	}
}

void solve(){
	for (int i = 0; i <= k; ++i){
		dijkstra(p[i]);
		for (int j = 0; j <= k; ++j)
			edges[i][j] = dist[ p[j] ];
	}
	for (int i = 0; i <= 1 << (k + 1); ++i)
		for (int j = 0; j <= k; ++j)
			mat[i][j] = inf;
	mat[1][0] = 0;
	for (int i = 0; i < 1 << (k + 1); ++i)
		for (int j = 0; j <= k; ++j)
			if ((1 << j) & i)
				for (int ii = 0; ii <= k; ++ii)
					if ((1 << ii) & i)
						mat[i][j] = min(mat[i][j], mat[i ^ (1 << j)][ii] + edges[j][ii]);
	printf("%d", mat[(1 << (k + 1)) - 1][k]);
	fclose(stdout);
}

int main(){
	freopen("ubuntzei.out", "w", stdout);
	read();
	solve();

	return 0;
}