結果
問題 |
No.898 tri-βutree
|
ユーザー |
![]() |
提出日時 | 2022-05-06 16:42:32 |
言語 | C++17 (gcc 13.3.0 + boost 1.87.0) |
結果 |
AC
|
実行時間 | 289 ms / 4,000 ms |
コード長 | 3,992 bytes |
コンパイル時間 | 2,762 ms |
コンパイル使用メモリ | 219,624 KB |
最終ジャッジ日時 | 2025-01-29 02:43:39 |
ジャッジサーバーID (参考情報) |
judge4 / judge1 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
sample | AC * 1 |
other | AC * 21 |
ソースコード
#include <bits/stdc++.h> using namespace std; template <typename T> struct BinaryIndexedTree { int N; vector<T>bit; BinaryIndexedTree(){} BinaryIndexedTree(int x) { N = x; bit.resize(x+1); } void add(int x,T y) { while(x <= N) { bit[x] += y; x += x&-x; } } T sum(int x) { T res = 0; while(x) { res += bit[x]; x -= x&-x; } return res; } inline T sum(int l, int r) {//[l,r] return sum(r)-sum(l-1); } inline T operator[](int k) { return sum(k)-sum(k-1); } }; struct HLD { vector<int>p,sz,in,nxt; BinaryIndexedTree<long long> bit; void dfs1(vector<vector<int>>&c,int v = 0) { sz[v] = 1; for(int &w:c[v]) { dfs1(c,w); sz[v] += sz[w]; if(sz[w] > sz[c[v][0]]) { swap(w,c[v][0]); } } } void dfs2(vector<vector<int>>&c,int &t,int v = 0) { in[v] = t; t++; for(int w:c[v]) { if(w == c[v][0]) { nxt[w] = nxt[v]; } else { nxt[w] = w; } dfs2(c,t,w); } } HLD(vector<long long>&A,vector<int>&p,vector<vector<int>>&c):p(p) { int N = A.size(); sz.resize(N,0); dfs1(c); in.resize(N,0); nxt.resize(N,0); int t = 0; dfs2(c,t); vector<long long>tmp(N); for(int i = 0; i < N; i++) { tmp[in[i]] = A[i]; } BinaryIndexedTree<long long>init(tmp.size()); for(int i = 0; i < tmp.size(); i++) { init.add(i+1,tmp[i]); } bit = init; } int lca(int u,int v) { while(true) { if(in[u] > in[v]) { swap(u,v); } if(nxt[u] == nxt[v]) { return u; } v = p[nxt[v]]; } } void update(int v,long long x) { bit.add(in[v]+1,x); } long long query(int u,int v) { int w = lca(u,v); long long ans = 0; while(nxt[u] != nxt[w]) { ans += bit.sum(in[nxt[u]]+1,in[u]+1); u = p[nxt[u]]; } ans += bit.sum(in[w]+2,in[u]+1); while(nxt[v] != nxt[w]) { ans += bit.sum(in[nxt[v]]+1,in[v]+1); v = p[nxt[v]]; } ans += bit.sum(in[w]+2,in[v]+1); return ans; } }; int now = 0; int cnt[100100]; void dfs(int n,vector<vector<int>>&c) { cnt[n] = now; now++; for(int i:c[n]) { dfs(i,c); } } bool chmax(int &x,int y) { if(x < y) { x = y; return true; } return false; } int main() { ios::sync_with_stdio(false); cin.tie(nullptr); int N; cin >> N; vector<vector<pair<int,int>>>ki(N); for(int i = 0; i < N-1; i++) { int u,v,w; cin >> u >> v >> w; ki[u].push_back({v,w}); ki[v].push_back({u,w}); } vector<int>p(N,-1); vector<vector<int>>c(N); queue<int>que; que.push(0); vector<long long>A(N); while (!que.empty()) { int x = que.front(); que.pop(); for(auto i:ki[x]) { if(i.first != 0 && p[i.first] == -1) { p[i.first] = x; c[x].push_back(i.first); que.push(i.first); A[i.first] = i.second; } } } HLD hld(A,p,c); dfs(0,c); int Q; cin >> Q; while (Q--) { int K = 3; vector<int>A(K); vector<pair<int,int>>tmp; for(int i = 0; i < K; i++) { cin >> A[i]; tmp.push_back({cnt[A[i]],A[i]}); } sort(tmp.begin(),tmp.end()); long long ans = 0; for(int i = 0; i < K; i++) { ans += hld.query(tmp[i].second,tmp[(i+1)%K].second); } cout << ans/2 << '\n'; } }