結果
問題 | No.386 貪欲な領主 |
ユーザー | btk |
提出日時 | 2016-07-01 23:51:16 |
言語 | C++14 (gcc 13.3.0 + boost 1.87.0) |
結果 |
AC
|
実行時間 | 212 ms / 2,000 ms |
コード長 | 1,627 bytes |
コンパイル時間 | 2,019 ms |
コンパイル使用メモリ | 175,796 KB |
実行使用メモリ | 34,528 KB |
最終ジャッジ日時 | 2024-10-12 19:10:52 |
合計ジャッジ時間 | 3,562 ms |
ジャッジサーバーID (参考情報) |
judge2 / judge5 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
other | AC * 16 |
ソースコード
#include<bits/stdc++.h> using namespace std; struct INIT{ INIT(){ ios::sync_with_stdio(false); cin.tie(0); } }init; typedef vector<int> V; typedef vector<int> E; typedef vector<E> Graph; typedef long long LL; typedef vector<LL> VL; void make_tree(int v, Graph &G, E &P, Graph &C, V& D,VL &sum) { for (auto& e : G[v]) { if (e!= P[v]) { C[v].push_back(e); D[e] = D[v]+1; P[e] = v; sum[e]+=sum[v]; make_tree(e, G, P, C, D,sum); } } } //lcaの準備 void build_PP(E& P,vector<V>& PP){ int N = P.size(); for(int i = 0; i < N; i++)PP[0][i] = P[i]; for(int k = 0,f=1;f; k++){ f=0; for(int i = 0; i < N; i++){ if(PP[k][i]<0)PP[k+1][i]=-1; else {PP[k+1][i]=PP[k][PP[k][i]];f=1;} } } } int lca(int u,int v,V& D,vector<V> &PP){ if(D[u] > D[v])swap(u,v); for(int k = 0,d;(d=D[v]-D[u]); k++)if((d >> k) & 1)v=PP[k][v]; if(u==v)return v; for(int k = PP.size() - 1; k >=0 ; k--){ if(PP[k][u]!=PP[k][v]){ u=PP[k][u]; v=PP[k][v]; } } return PP[0][u]; } #define rep(i,n) for(auto i=(n)*0;i<n;i++) int main(){ int N; cin>>N; Graph g(N+1); g[N].push_back(0); rep(i,N-1){ int a,b; cin>>a>>b; g[a].push_back(b); g[b].push_back(a); } vector<V> pp(20,V(N+1,-1)); Graph child(N+1); V p(N+1),depth(N+1); VL U(N+1); p[N]=-1;U[N]=0;depth[N]=0; rep(i,N)cin>>U[i]; make_tree(N,g,p,child,depth,U); build_PP(p,pp); LL res=0; int M; cin>>M; rep(i,M){ int a,b,c; cin>>a>>b>>c; int ca=lca(a,b,depth,pp); int cp=p[ca]; res+=c*(U[a]+U[b]-U[ca]-U[cp]); } cout<<res<<endl; }