제출 #1352385

#제출 시각아이디문제언어결과실행 시간메모리
1352385tkm_algorithmsCities (BOI16_cities)C++20
0 / 100
253 ms103480 KiB
#include <bits/stdc++.h>

using namespace std;
using ll = long long;
#define int ll
using P = pair<int, int>;
#define all(x) x.begin(), x.end()
#define rep(x,s,e) for (auto x=(s)-((s)>(e));x!=(e)-((s)>(e));((s)<(e)?x++:x--))
#define sz(x) (int)x.size()
const char nl = '\n';
const int N = 1e5+10;
int par[6][N][17];
const int inf = 1e14+10;
int d[6][N];
vector<P> g[N];
vector<int> sons[N];
int pr[N], dep[6][N];

struct X {
	int par, nd, c;
};

int n, k, m;

struct cmp {
    bool operator()(const X& a, const X& b) {
        return a.c > b.c;  // min-heap based on c
    }
};
int b[N];

void calc(int idx, int nd) {
	priority_queue<X, vector<X>, cmp> pq;
	rep(j, 1, n+1)d[idx][j] = inf;
	d[idx][nd] = 0, pq.push({-1, nd, 0});
	while (!pq.empty()) {
		auto x = pq.top(); pq.pop();
		if (x.c != d[idx][x.nd])continue;
		par[idx][x.nd][0] = x.par;
		//cout << x.nd << " " << x.c << nl;
		dep[idx][x.nd] = dep[idx][x.par]+1;
		rep(j, 1, 17) {
			if (par[idx][nd][j-1] == -1)break;
			par[idx][nd][j] = par[idx][par[idx][nd][j-1]][j-1];
		}
		for (auto [j, w]: g[x.nd]) {
			if (d[idx][j] > x.c+w)
				d[idx][j] = x.c+w,
				pq.push({x.nd, j, x.c+w});
		}
	}
}

int lca(int x, int y, int idx) {
	if (dep[idx][y] > dep[idx][x])swap(x, y);
	rep(i, 17, 0) {
		if (par[idx][x][i] == -1)continue;
		if (dep[idx][par[idx][x][i]] >= dep[idx][y])x = par[idx][x][i];
	}
	
	if (x == y)return x;
	rep(i, 17, 0) {
		if (par[idx][x][i] != par[idx][y][i])
			x = par[idx][x][i],
			y = par[idx][y][i];
	}
	return par[idx][x][0];
}

int build(vector<int> &a, int pos = 1) {
	if (pos == sz(a)) {
		//cout << "----------" << nl;
		int sum = 0;
		rep(i, 0, k) {
			rep(j, 1, (1<<sz(sons[a[i]]))) {
				int pp = ((__builtin_popcount(j)&1)?1:-1);
				int l = -1;
				rep(p, 0, 17)
					if ((1<<p)&j) {
						if (~l)l = lca(l, sons[a[i]][p], b[a[i]]);
						else l = sons[a[i]][p];
					}
				sum += pp*d[b[a[i]]][l];
			}
		}
		//cout << "----------" << nl;
		return sum;
	}
	int mn = inf;
	rep(i, 0, pos) {
		sons[a[i]].push_back(a[pos]);
		pr[a[pos]] = a[i];
		mn = min(mn, build(a, pos+1));
		sons[a[i]].pop_back();
		pr[a[pos]] = -1;
	}
	return mn;
}

void solve() {
	memset(par, -1, sizeof par);
	cin >> n >> k >> m;
	vector<int> a(k);
	rep(i, 0, k) {
		cin >> a[i];
		b[a[i]] = i;
	}
	rep(i, 0, m) {
		int u, v, w; cin >> u >> v >> w;
		g[u].push_back({v, w});
		g[v].push_back({u, w});
	}
	
	sort(all(a));
	rep(i, 0, k)calc(b[a[i]], a[i]);
	
	//calc(1, 3);
	
	//cout << d[1][1] << " " << d[1][4]  << nl;
	
	int res = inf;
	do {
		res = min(res, build(a));
	} while (next_permutation(all(a)));
	cout << res << nl;
}

int32_t main() {
    ios_base::sync_with_stdio(0);
    cin.tie(0);
    solve();
    return 0;
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...