Advertisement
Alex_tz307

TrumpLandia

Mar 15th, 2021
194
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 3.49 KB | None | 0 0
  1. #include <bits/stdc++.h>
  2.  
  3. using namespace std;
  4. using int64 = long long;
  5.  
  6. ifstream fin("trumplandia.in");
  7. ofstream fout("trumplandia.out");
  8.  
  9. class edge {
  10.     public:
  11.         int u, v, w, ind;
  12.  
  13.         void read() {
  14.             fin >> u >> v >> w;
  15.         }
  16.  
  17.         bool operator < (const edge &A) const {
  18.             return w < A.w;
  19.         }
  20. };
  21.  
  22. class DSU {
  23.     public:
  24.         int N;
  25.         vector<int> p, r;
  26.  
  27.         DSU(int n) : N(n) {
  28.             p.resize(N + 1);
  29.             iota(p.begin(), p.end(), 0);
  30.             r.assign(N + 1, 1);
  31.         }
  32.  
  33.         int get(int x) {
  34.             if(x == p[x])
  35.                 return x;
  36.             return p[x] = get(p[x]);
  37.         }
  38.  
  39.         bool unite(int u, int v) {
  40.             int x = get(u),
  41.                 y = get(v);
  42.             if(x == y)
  43.                 return false;
  44.             if(r[x] > r[y]) {
  45.                 p[y] = x;
  46.                 r[x] += r[y];
  47.             }
  48.             else {
  49.                 p[x] = y;
  50.                 r[y] += r[x];
  51.             }
  52.             return true;
  53.         }
  54. };
  55.  
  56. class lca_node {
  57.     public:
  58.         int prv, mx;
  59. };
  60.  
  61. const int NMAX = 2e5 + 2;
  62. int N, M, Q, lg2[NMAX], depth[NMAX];
  63. edge edges[NMAX];
  64. bool used[NMAX];
  65. int64 cost, sol[NMAX];
  66. vector<pair<int,int>> G[NMAX];
  67. lca_node ancestor[NMAX][19];
  68.  
  69. void dfs(const int &u, const int &parent, const int &edge_value) {
  70.     ancestor[u][0] = lca_node{parent, edge_value};
  71.     for(int lift = 1; lift < 19; ++lift) {
  72.         lca_node &p = ancestor[u][lift];
  73.         lca_node half_ancestor = ancestor[u][lift - 1];
  74.         p.prv = ancestor[half_ancestor.prv][lift - 1].prv;
  75.         p.mx = max(half_ancestor.mx, ancestor[half_ancestor.prv][lift - 1].mx);
  76.     }
  77.     for(const pair<int,int> &v : G[u])
  78.         if(v.first != parent) {
  79.             depth[v.first] = depth[u] + 1;
  80.             dfs(v.first, u, v.second);
  81.         }
  82. }
  83.  
  84. void max_self(int &a, int b) {
  85.     a = max(a, b);
  86. }
  87.  
  88. int query_max(int u, int v) {
  89.     if(depth[u] < depth[v])
  90.         swap(u, v);
  91.     int ans = 0;
  92.     for(int lift = 18; lift >= 0; --lift)
  93.         if(depth[u] - (1 << lift) >= depth[v]) {
  94.             lca_node node = ancestor[u][lift];
  95.             max_self(ans, node.mx);
  96.             u = node.prv;
  97.         }
  98.     if(u == v)
  99.         return ans;
  100.     for(int lift = 18; lift >= 0; --lift) {
  101.         lca_node x = ancestor[u][lift], y = ancestor[v][lift];
  102.         if(x.prv != y.prv) {
  103.             max_self(ans, x.mx), max_self(ans, y.mx);
  104.             u = x.prv, v = y.prv;
  105.         }
  106.     }
  107.     return max({ans, ancestor[u][0].mx, ancestor[v][0].mx});
  108. }
  109.  
  110. int main() {
  111.     fin >> N >> M >> Q;
  112.     for(int i = 1; i <= M; ++i) {
  113.         edge &p = edges[i];
  114.         p.read();
  115.         p.ind = i;
  116.     }
  117.     sort(edges + 1, edges + M + 1);
  118.     DSU tree(N);
  119.     for(int i = 1; i <= M; ++i)
  120.         if(tree.unite(edges[i].u, edges[i].v)) {
  121.             edge e = edges[i];
  122.             cost += e.w;
  123.             used[e.ind] = true;
  124.             G[e.u].emplace_back(e.v, e.w);
  125.             G[e.v].emplace_back(e.u, e.w);
  126.         }
  127.     for(int i = 2; i <= N; ++i)
  128.         lg2[i] = lg2[i >> 1] + 1;
  129.     dfs(1, 0, 0);
  130.     for(int i = 1; i <= M; ++i) {
  131.         edge e = edges[i];
  132.         if(used[e.ind])
  133.             sol[e.ind] = cost;
  134.         else
  135.             sol[e.ind] = cost + e.w - query_max(e.u, e.v);
  136.     }
  137.     fout << cost << '\n';
  138.     for(int q = 0; q < Q; ++q) {
  139.         int index;
  140.         fin >> index;
  141.         fout << sol[index] << '\n';
  142.     }
  143. }
  144.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement