Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include<bits/stdc++.h>
- using namespace std;
- const int MX = (1<<18);
- int n;
- void upd(int *bit , int x , int V){
- while(x <= n){
- bit[x] += V;
- x += x & (-x);
- }
- }
- int get(int *bit , int x){
- int ret = 0;
- while(x > 0){
- ret += bit[x];
- x -= x &(-x);
- }
- return ret;
- }
- int bit[MX] , lazybit[MX] , temp[MX];
- vector < int > in ;
- vector < pair < int , int > > lazy[MX];
- int ans[MX];
- void insert_(int x , int stop , int W){
- upd(bit , x , 1);
- upd(lazybit , x , W);
- lazy[stop].push_back({x , -W});
- in.push_back(x);
- }
- void clear_sack(){
- for(int j = 0 ; j < in.size() ; j++){
- for(auto pp : lazy[j])
- upd(lazybit , pp.first , pp.second);
- lazy[j].clear();
- ans[in[j]] += get(lazybit , in[j]);
- upd(bit , in[j] , -1);
- }
- in.clear();
- }
- int sz[MX] , maxy[MX] , parent[MX];
- vector < int > v[MX];
- vector < int > paths[MX];
- void format(){
- clear_sack();
- for(int j = 1 ; j <= n ; j++){
- v[j].clear();
- paths[j].clear();
- maxy[j] = 0;
- parent[j] = 0;
- bit[j] = lazybit[j] = 0;
- temp[j] = ans[j] = 0;
- }
- }
- void dfslight(int x , int root){
- paths[root].push_back(x);
- for(auto nxt : v[x]){
- if(nxt == parent[x]) continue;
- dfslight(nxt , root);
- }
- }
- int W[MX];
- void dfs(int x , int p){
- ans[x] = 0;
- for(auto nxt : v[x]){
- if(nxt == p || nxt == maxy[x]) continue;
- dfslight(nxt , nxt);
- dfs(nxt , x);
- }
- clear_sack();
- if(maxy[x])
- dfs(maxy[x] , x);
- int stop = in.size();
- for(auto nxt : v[x]){
- if(nxt == p || nxt == maxy[x]) continue;
- for(auto P : paths[nxt]){
- ans[P] += get(bit , P) * W[x];
- }
- for(auto P : paths[nxt])
- insert_(P , stop , W[x]);
- }
- reverse(v[x].begin() , v[x].end());
- for(auto nxt : v[x]){
- if(nxt == p || nxt == maxy[x]) continue;
- for(auto P : paths[nxt])
- ans[P] += get(temp , P) * W[x];
- for(auto P : paths[nxt])
- upd(temp , P , 1);
- }
- for(auto nxt : v[x]) if(nxt != p && nxt != maxy[x]) for(auto P : paths[nxt]) upd(temp , P , -1);
- ans[x] += get(bit , x) * W[x];
- insert_(x , in.size() , W[x]);
- }
- void Pdfs(int x , int p){
- sz[x] = 1;
- for(auto nxt : v[x]){
- if(nxt == p) continue;
- parent[nxt] = x;
- Pdfs(nxt , x);
- sz[x] += sz[nxt];
- }
- for(auto nxt : v[x]){
- if(nxt == p) continue;
- if(sz[nxt] > sz[x]/2){
- maxy[x] = nxt;
- }
- }
- }
- void solve(){
- cin>>n;
- format();
- for(int j = 1 ; j <= n ; j++){
- scanf("%d",&W[j]);
- }
- for(int j = 1 ; j <= n ; j++){
- int p;
- scanf("%d",&p);
- if(j == 1) continue;
- v[p].push_back(j);
- v[j].push_back(p);
- }
- Pdfs(1 , -1);
- dfs(1 , -1);
- clear_sack();
- for(int j = 2 ; j <= n ; j++){
- if(j > 2) printf(" ");
- printf("%d",ans[j]);
- }
- puts("");
- }
- int main(){
- int T;
- cin>>T; while(T--) solve();
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement