Advertisement
GuilhermeCpp

Trip Discount

Aug 23rd, 2023
1,302
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 4.58 KB | None | 0 0
  1. #include <bits/stdc++.h>
  2. using namespace std;      
  3.  
  4. #define NMAX 10010
  5. #define LOGMAX 16
  6. #define fi first
  7. #define se second
  8. #define pb push_back
  9. #define mp make_pair
  10.  
  11. typedef long long ll;
  12. typedef pair< ll, ll > pll;
  13.  
  14. ll n;
  15. vector< pll > grafo[NMAX];
  16.  
  17. ll pai[NMAX];
  18. ll wpai[NMAX];
  19. ll level[NMAX];
  20.  
  21. ll vet[NMAX];
  22.  
  23. ll anc[NMAX][LOGMAX + 1LL];
  24.  
  25. ll in[NMAX];
  26. ll out[NMAX];
  27. ll who[NMAX];
  28. vector< ll > order;
  29.  
  30. ll accu[NMAX];
  31.  
  32. ll bestDist;
  33. pll best;
  34.  
  35. pll invalid = {-1LL, -1LL};
  36.  
  37. bool passed[NMAX];
  38.  
  39. pll st[4LL * NMAX];
  40. ll la[4LL * NMAX];
  41.  
  42. void DFS(ll u, ll d)
  43. {
  44.  
  45.     anc[u][0] = pai[u];
  46.     for(ll i = 1;i <= LOGMAX;i++)
  47.         anc[u][i] = anc[ anc[u][i - 1] ][i - 1];
  48.  
  49.     in[u] = order.size();
  50.    
  51.     vet[in[u]] = d;
  52.     who[in[u]] = u;
  53.  
  54.     order.pb(u);
  55.  
  56.     ll v, w;
  57.    
  58.     for(auto viz : grafo[u])
  59.     {
  60.    
  61.         w = viz.fi;
  62.         v = viz.se;
  63.        
  64.         if(pai[v] != 0LL) continue;
  65.        
  66.         pai[v] = u;
  67.         wpai[v] = w;
  68.         level[v] = level[u] + 1;
  69.        
  70.         DFS(v, d + w);
  71.  
  72.     }
  73.    
  74.     out[u] = order.size() - 1LL;
  75.  
  76.     return;
  77.  
  78. }
  79.  
  80. void DFS(ll u)
  81. {
  82.  
  83.     for(ll i = 1;i <= n;i++) pai[i] = 0LL;
  84.  
  85.     order.clear();
  86.  
  87.     pai[u] = u;
  88.     wpai[u] = 0;
  89.     level[u] = 0LL;
  90.     DFS(u, 0LL);
  91.    
  92.     return;
  93.  
  94. }
  95.  
  96. ll LCA(ll u, ll v)
  97. {
  98.  
  99.     if(level[u] < level[v]) swap(u, v);
  100.    
  101.     ll i;
  102.  
  103.     for(i = LOGMAX;i >= 0;i--)
  104.     {
  105.    
  106.         if(level[u] - (1LL << i) >= level[v]) u = anc[u][i];
  107.    
  108.     }
  109.    
  110.     if(u != v)
  111.     {
  112.  
  113.         for(i = LOGMAX;i >= 0;i--)
  114.         {
  115.        
  116.             if(anc[u][i] != anc[v][i])
  117.             {
  118.            
  119.                 u = anc[u][i];
  120.                 v = anc[v][i];
  121.            
  122.             }
  123.        
  124.         }
  125.        
  126.         u = anc[u][0];
  127.         v = anc[v][0];
  128.    
  129.     }
  130.    
  131.     return u;
  132.  
  133. }
  134.  
  135. ll changeEdges(ll u)
  136. {
  137.  
  138.     ll v, w, x;
  139.  
  140.     x = accu[u];
  141.    
  142.     for(auto viz : grafo[u])
  143.     {
  144.    
  145.         w = viz.fi;
  146.         v = viz.se;
  147.        
  148.         if(v == pai[u]) continue;
  149.        
  150.         x += changeEdges(v);
  151.    
  152.     }
  153.    
  154.     wpai[u] = x * wpai[u];
  155.    
  156.     return x;
  157.  
  158. }
  159.  
  160. pll findDiameter(ll u)
  161. {
  162.  
  163.     ll v, w;
  164.  
  165.     pll ma, ma2, x;
  166.    
  167.     ma = invalid;
  168.     ma2 = invalid;
  169.  
  170.     for(auto viz : grafo[u])
  171.     {
  172.        
  173.         w = viz.fi;
  174.         v = viz.se;
  175.        
  176.         if(v == pai[u]) continue;
  177.    
  178.         x = findDiameter(v);
  179.         x.fi += w;
  180.        
  181.         ma2 = max(ma2, x);
  182.        
  183.         if(ma < ma2) swap(ma, ma2);
  184.        
  185.     }
  186.    
  187.     if(ma == invalid) ma = {0LL, u};
  188.     if(ma2 == invalid) ma2 = {0LL, u};
  189.    
  190.     if(bestDist < ma.fi + ma2.fi)
  191.     {
  192.        
  193.         bestDist = ma.fi + ma2.fi;
  194.         best = {ma.se, ma2.se};
  195.    
  196.     }
  197.    
  198.     return ma;
  199.  
  200. }
  201.  
  202. void Lazy(ll idx, ll l, ll r)
  203. {
  204.  
  205.     if(la[idx] == 0LL) return;
  206.    
  207.     st[idx].fi += la[idx];
  208.    
  209.     ll nxt = (idx << 1LL);
  210.    
  211.     if(l != r)
  212.     {
  213.    
  214.         la[nxt] += la[idx];
  215.         la[nxt + 1LL] += la[idx];
  216.    
  217.     }
  218.    
  219.     la[idx] = 0;
  220.    
  221.     return;
  222.  
  223. }
  224.  
  225. void Build(ll idx, ll l, ll r)
  226. {
  227.    
  228.     if(l == r)
  229.     {
  230.    
  231.         st[idx] = {vet[l], who[l]};
  232.         la[idx] = 0LL;
  233.        
  234.         return;
  235.    
  236.     }
  237.    
  238.     ll nxt = (idx << 1LL), mid = ((l + r) >> 1LL);
  239.    
  240.     Build(nxt, l, mid);
  241.     Build(nxt + 1LL, mid + 1LL, r);
  242.  
  243.     st[idx] = max(st[nxt], st[nxt + 1LL]);
  244.  
  245.     return;
  246.    
  247. }
  248.  
  249. void Update(ll idx, ll l, ll r, ll a, ll b, ll val)
  250. {
  251.  
  252.     Lazy(idx, l, r);
  253.  
  254.     if(a <= l && r <= b)
  255.     {
  256.    
  257.         la[idx] += val;
  258.        
  259.         Lazy(idx, l, r);
  260.    
  261.         return;
  262.    
  263.     }
  264.    
  265.     if(r < a || b < l) return;
  266.    
  267.     ll nxt = (idx << 1LL), mid = ((l + r) >> 1LL);
  268.    
  269.     Update(nxt, l, mid, a, b, val);
  270.     Update(nxt + 1LL, mid + 1LL, r, a, b, val);
  271.  
  272.     st[idx] = max(st[nxt], st[nxt + 1LL]);
  273.  
  274.     return;
  275.    
  276. }
  277.  
  278. ll Erase(ll u)
  279. {
  280.    
  281.     ll v, x, sum;
  282.    
  283.     pll *edge;
  284.    
  285.     sum = 0LL;
  286.  
  287.     while(passed[u] == false)
  288.     {
  289.    
  290.         sum += wpai[u];
  291.    
  292.         Update(1LL, 0LL, n - 1LL, in[u], out[u], -wpai[u]);
  293.        
  294.         passed[u] = true;
  295.        
  296.         u = pai[u];
  297.        
  298.     }
  299.    
  300.     return sum;
  301.  
  302. }
  303.  
  304. int main()
  305. {
  306.  
  307.     ios_base::sync_with_stdio(0);
  308.     cin.tie(0);
  309.     cout.tie(0);
  310.  
  311.     ll tt, q, k, u, v, w, resp, i, j;
  312.    
  313.     cin >> tt;     
  314.    
  315.     while(tt--)
  316.     {
  317.    
  318.         resp = 0LL;
  319.         bestDist = -1LL;
  320.    
  321.         cin >> n >> k >> q;
  322.        
  323.         for(i = 1;i <= n;i++) grafo[i].clear();
  324.        
  325.         for(i = 1;i <= n;i++) accu[i] = 0LL;   
  326.        
  327.         for(i = 2;i <= n;i++)
  328.         {
  329.        
  330.             cin >> u >> v >> w;
  331.            
  332.             grafo[u].pb({w, v});
  333.             grafo[v].pb({w, u});
  334.        
  335.         }
  336.        
  337.         DFS(1LL);
  338.        
  339.         while(q--)
  340.         {
  341.        
  342.             cin >> u >> v;
  343.        
  344.             accu[u] += 1LL;
  345.             accu[v] += 1LL;
  346.             accu[LCA(u, v)] -= 2LL;
  347.        
  348.         }
  349.        
  350.         changeEdges(1LL);
  351.    
  352.         for(i = 1;i <= n;i++) resp += wpai[i];
  353.        
  354.         // Remontando grafo
  355.    
  356.         for(i = 1;i <= n;i++) grafo[i].clear();
  357.        
  358.         for(i = 2;i <= n;i++)
  359.         {
  360.        
  361.             u = i;
  362.             v = pai[i];
  363.             w = wpai[i];
  364.        
  365.             grafo[u].pb({w, v});
  366.             grafo[v].pb({w, u});
  367.        
  368.         }  
  369.    
  370.         findDiameter(1LL);
  371.        
  372.         k--; // choose best.fi
  373.         DFS(best.fi);
  374.         passed[best.fi] = true;
  375.        
  376.         Build(1LL, 0LL, n - 1LL);
  377.        
  378.         while(k--) resp -= Erase(st[1LL].se);
  379.        
  380.         cout << resp << "\n";
  381.    
  382.     }
  383.  
  384.     return 0;
  385.  
  386. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement