結果
問題 | No.114 遠い未来 |
ユーザー | wanui |
提出日時 | 2024-07-30 00:35:40 |
言語 | C++17 (gcc 12.3.0 + boost 1.83.0) |
結果 |
TLE
|
実行時間 | - |
コード長 | 6,224 bytes |
コンパイル時間 | 3,140 ms |
コンパイル使用メモリ | 230,936 KB |
実行使用メモリ | 10,400 KB |
最終ジャッジ日時 | 2024-07-30 00:35:54 |
合計ジャッジ時間 | 13,654 ms |
ジャッジサーバーID (参考情報) |
judge2 / judge3 |
(要ログイン)
テストケース
テストケース表示入力 | 結果 | 実行時間 実行使用メモリ |
---|---|---|
testcase_00 | AC | 49 ms
6,812 KB |
testcase_01 | AC | 1,938 ms
6,940 KB |
testcase_02 | AC | 323 ms
6,940 KB |
testcase_03 | AC | 55 ms
6,940 KB |
testcase_04 | AC | 2 ms
6,940 KB |
testcase_05 | AC | 16 ms
6,940 KB |
testcase_06 | AC | 757 ms
6,944 KB |
testcase_07 | AC | 2 ms
6,940 KB |
testcase_08 | AC | 2 ms
6,944 KB |
testcase_09 | AC | 39 ms
6,944 KB |
testcase_10 | AC | 318 ms
6,944 KB |
testcase_11 | TLE | - |
testcase_12 | -- | - |
testcase_13 | -- | - |
testcase_14 | -- | - |
testcase_15 | -- | - |
testcase_16 | -- | - |
testcase_17 | -- | - |
testcase_18 | -- | - |
testcase_19 | -- | - |
testcase_20 | -- | - |
testcase_21 | -- | - |
testcase_22 | -- | - |
testcase_23 | -- | - |
testcase_24 | -- | - |
testcase_25 | -- | - |
testcase_26 | -- | - |
testcase_27 | -- | - |
ソースコード
#include <bits/stdc++.h> // clang-format off using namespace std; using ll=long long; using ull=unsigned long long; using pll=pair<ll,ll>; const ll INF=4e18; void print0(){}; template<typename H,typename... T> void print0(H h,T... t){cout<<h;print0(t...);} void print1(){print0("\n");}; template<typename H,typename... T>void print1(H h,T... t){print0(h);if(sizeof...(T)>0)print0(" ");print1(t...);} #define debug1(a) { cerr<<#a<<":"<<a<<endl; } #define debug2(a,b) { cerr<<#a<<":"<<a<<" "<<#b<<":"<<b<<endl; } #define debug3(a,b,c) { cerr<<#a<<":"<<a<<" "<<#b<<":"<<b<<" "<<#c<<":"<<c<<endl; } #define debug4(a,b,c,d) { cerr<<#a<<":"<<a<<" "<<#b<<":"<<b<<" "<<#c<<":"<<c<<" "<<#d<<":"<<d<<endl; } // clang-format on namespace SteinerTree { ll solve(vector<vector<pll>>& graph, vector<bool>& is_city) { ll N = graph.size(); ll K = 0; vector<ll> cityid(N, -1); for (ll u = 0; u < N; u++) { if (is_city[u]) { cityid[u] = K; K++; } } ll ans = INF; { vector<vector<ll>> dp(N, vector<ll>(1 << K, INF)); for (ll u = 0; u < N; u++) { if (cityid[u] >= 0) { ll city = cityid[u]; dp[u][1 << city] = 0; } dp[u][0] = 0; } for (ll s = 1; s < (1 << K); s++) { for (ll u = 0; u < N; u++) { for (ll j = s;; j = (j - 1) & s) { ll k = s ^ j; // 残り if (k > 0 && j > 0) { dp[u][s] = min(dp[u][s], dp[u][j] + dp[u][k]); } if (!j) break; } } priority_queue<pll, vector<pll>, greater<pll>> pq; for (ll u = 0; u < N; u++) { ll city = cityid[u]; if (dp[u][s] == INF) continue; pq.push({dp[u][s], u}); } vector<bool> done(N); while (pq.size()) { ll cost, u; tie(cost, u) = pq.top(); pq.pop(); if (done[u]) continue; done[u] = true; dp[u][s] = min(dp[u][s], cost); if (cityid[u] >= 0) { ll t = (1 << cityid[u]) | s; dp[u][t] = min(dp[u][t], cost); } for (auto e : graph[u]) { pq.push({e.second + cost, e.first}); } } } for (ll u = 0; u < N; u++) { ans = min(ans, dp[u][(1 << K) - 1]); } } return ans; } }; // namespace SteinerTree namespace LargeSolver { class unionfind { public: vector<ll> partition; vector<ll> rank; vector<ll> siz; ll n; unionfind(ll n_) { partition.resize(n_); rank.resize(n_); siz.resize(n_); for (ll x = 0; x < n_; x++) { partition[x] = x; rank[x] = 0; siz[x] = 1; } n = n_; } ll find(ll x) { if (partition[x] == x) { return x; } else { partition[x] = find(partition[x]); return partition[x]; } } void unite(ll x, ll y) { x = find(x); y = find(y); if (x == y) { return; } ll sx = siz[x]; ll sy = siz[y]; if (rank[x] < rank[y]) { partition[x] = y; } else { partition[y] = x; if (rank[x] == rank[y]) { rank[x]++; } } siz[find(x)] = sx + sy; } bool same(ll x, ll y) { return find(x) == find(y); } ll clstsize(ll x) { return siz[find(x)]; } vector<pair<ll, vector<ll>>> get_clusters() { vector<vector<ll>> con(n); for (ll i = 0; i < n; i++) { con[find(i)].push_back(i); } vector<pair<ll, vector<ll>>> result; for (ll i = 0; i < n; i++) { if (con[i].size() > 0) { vector<ll> members = con[i]; result.push_back({i, members}); } } return result; } }; ll solve(vector<vector<pll>>& graph, vector<bool>& is_city) { ll N = graph.size(); vector<ll> villages; for (ll u = 0; u < N; u++) { if (!is_city[u]) villages.push_back(u); } vector<pair<ll, pll>> edgs; for (ll u = 0; u < N; u++) { for (auto e : graph[u]) { ll v = e.first; ll c = e.second; if (u > v) continue; edgs.push_back({c, {u, v}}); } } sort(edgs.begin(), edgs.end()); ll ans = INF; ll m = villages.size(); for (ll i = 0; i < (1 << m); i++) { ll first_city = N; ll usenum = 0; vector<bool> use(N); for (ll u = 0; u < N; u++) { if (is_city[u]) { first_city = min(first_city, u); use[u] = true; usenum++; } } for (ll j = 0; j < m; j++) { if ((i >> j) & 1) { use[villages[j]] = true; usenum++; } } ll now = 0; auto uf = unionfind(N); for (auto e : edgs) { ll c = e.first; ll u = e.second.first; ll v = e.second.second; if (!use[u] || !use[v]) continue; if (!uf.same(u, v)) { uf.unite(u, v); now += c; } } if (uf.clstsize(first_city) == usenum) { ans = min(ans, now); } } return ans; } }; // namespace LargeSolver int main() { ll N, M, T; cin >> N >> M >> T; vector<vector<pll>> graph(N); for (ll i = 0; i < M; i++) { ll u, v, c; cin >> u >> v >> c; u--; v--; graph[u].push_back({v, c}); graph[v].push_back({u, c}); } vector<bool> is_city(N); for (ll i = 0; i < T; i++) { ll u; cin >> u; u--; is_city[u] = true; } if (T <= 13) { print1(SteinerTree::solve(graph, is_city)); } else { print1(LargeSolver::solve(graph, is_city)); } }