• CF1076E Vasya and a Tree


    可以把操作离线,每次开始遍历到一个节点,把以它为根的操作加上,结束时把这个点的操作删去。

    因为是(dfs),所以一个点对同一深度的贡献是一定的,可以用树状数组区间加减,求前缀和。

    但是因为是(dfs),完全可以把前缀和传入,就不需要树状数组了。

    #define B cout << "BreakPoint" << endl;
    #define O(x) cout << #x << " " << x << endl;
    #define O_(x) cout << #x << " " << x << " ";
    #define Msz(x) cout << "Sizeof " << #x << " " << sizeof(x)/1024/1024 << " MB" << endl;
    #include<cstdio>
    #include<cmath>
    #include<iostream>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    #include<set>
    #define LL long long
    const int inf = 1e9 + 9;
    const int N = 6e5 + 5;
    using namespace std;
    inline int read() {
    	int s = 0,w = 1;
    	char ch = getchar();
    	while(ch < '0' || ch > '9') {
    		if(ch == '-')
    			w = -1;
    		ch = getchar();
    	}
    	while(ch >= '0' && ch <= '9') {
    		s = s * 10 + ch - '0';
    		ch = getchar();
    	}
    	return s * w;
    }
    int head[N],to[N],nxt[N],cnt;
    void add(int x,int y) {
    	to[++cnt] = y;
    	nxt[cnt] = head[x];
    	head[x] = cnt;
    }
    int n,m;
    struct node {
    	int d,x;
    	inline node() {}
    	inline node(int __d, int __x) :d(__d), x(__x){}
    };
    vector<node> s[N];
    LL c[N],ans[N];
    void dfs(int u,int fa,int dep,LL sum) {
    	for(auto it = s[u].begin();it != s[u].end();it++) {
    		c[dep] += it->x;
    		if(dep + it->d + 1 <= n) c[dep + it->d + 1] -= it->x;
    	}
    	sum += c[dep],ans[u] = sum;
    	for(int i = head[u];i;i = nxt[i]) {
    		int v = to[i];
    		if(v != fa) dfs(v,u,dep + 1,sum);
    	}
    	for(auto it = s[u].begin();it != s[u].end();it++) {
    		c[dep] -= it -> x;
    		if(dep + it -> d + 1 <= n) c[dep + it -> d + 1] += it -> x;
    	}
    }
    int main() {
    	n = read();
    	for(int i = 1;i < n;i++) {
    		int x = read(),y = read();
    		add(x,y),add(y,x);
    	}
    	m = read();
    	for(int i = 1;i <= m;i++) {
    		int v = read(),d = read(),x = read();
    		s[v].push_back(node(d,x));
    	}
    	dfs(1,0,0,0);
    	for(int i = 1;i <= n;i++) printf("%lld ", ans[i]);
    	return 0;
    }
    
  • 相关阅读:
    [转]Ubuntu设置Redhat风格的SHELL提示符PS1属性
    [转]Ubuntu Adsl 上网
    [转]Bash中的PS1详解
    Verilog 关于用task仿真应注意的一个问题
    [转]提高编程技能最有效的方法
    [转]ubuntu 终端常用命令
    [转]VMware Workstation 7.1 正式版 For Linux
    [转]Vim基本操作
    [转]Ubuntu Linux下设置IP的配置命令
    xilinxftp.newlocation
  • 原文地址:https://www.cnblogs.com/excellent-zzy/p/12410909.html
Copyright © 2020-2023  润新知