CodeForces 396C On Changing Tree
On Changing Tree
This problem will be judged on CodeForces. Original ID: 396C
64-bit integer IO format: %I64d Java class name: (Any)
Initially all vertices contain number 0. Then come q queries, each query has one of the two types:
- The format of the query: 1 v x k. In response to the query, you need to add to the number at vertex v number x; to the numbers at the descendants of vertex v at distance 1, addx - k; and so on, to the numbers written in the descendants of vertex v at distance i, you need to add x - (i·k). The distance between two vertices is the number of edges in the shortest path between these vertices.
- The format of the query: 2 v. In reply to the query you should print the number written in vertex v modulo 1000000007 (109 + 7).
Process the queries given in the input.
Input
The first line contains integer n (1 ≤ n ≤ 3·105) — the number of vertices in the tree. The second line contains n - 1 integers p2, p3, ... pn (1 ≤ pi < i), where pi is the number of the vertex that is the parent of vertex i in the tree.
The third line contains integer q (1 ≤ q ≤ 3·105) — the number of queries. Next q lines contain the queries, one per line. The first number in the line is type. It represents the type of the query. If type = 1, then next follow space-separated integers v, x, k (1 ≤ v ≤ n; 0 ≤ x < 109 + 7; 0 ≤ k < 109 + 7). If type = 2, then next follows integer v (1 ≤ v ≤ n) — the vertex where you need to find the value of the number.
Output
For each query of the second type print on a single line the number written in the vertex from the query. Print the number modulo 1000000007 (109 + 7).
Sample Input
3
1 1
3
1 1 2 1
2 1
2 2
2
1
Hint
You can read about a rooted tree here: http://en.wikipedia.org/wiki/Tree_(graph_theory).
Source
#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
const int maxn = ;
const int mod = ;
vector<int>g[maxn];
LL c[][maxn],val[];
int n,m,L[maxn],R[maxn],d[maxn],clk;
void update(int i){
while(i < maxn){
c[][i] += val[];
c[][i] += val[];
c[][i] %= mod;
c[][i] %= mod;
i += i&-i;
}
}
LL query(int i){
LL sum[] = {},dep = d[i];
i = L[i];
while(i > ){
sum[] += c[][i];
sum[] += c[][i];
sum[] %= mod;
sum[] %= mod;
i -= i&-i;
}
return ((sum[] - dep*sum[])%mod + mod)%mod;
}
void dfs(int u,int dep){
L[u] = ++clk;
d[u] = dep;
for(int i = g[u].size()-; i >= ; --i)
dfs(g[u][i],dep+);
R[u] = clk;
}
int main(){
int u,op,x,y,z;
while(~scanf("%d",&n)){
for(int i = clk = ; i <= n; ++i) g[i].clear();
for(int i = ; i <= n; ++i){
scanf("%d",&u);
g[u].push_back(i);
}
dfs(,);
memset(c,,sizeof c);
scanf("%d",&m);
while(m--){
scanf("%d%d",&op,&x);
if(op == ){
scanf("%d%d",&y,&z);
val[] = ((LL)y + (LL)d[x]*z)%mod;
val[] = z;
update(L[x]);
val[] = -val[];
val[] = -val[];
update(R[x]+);
}else printf("%I64d\n",query(x));
}
}
return ;
}
最新文章
- 比较.NET程序集(DLL或EXE)是否相同
- sqlserver 自增ID插入指定数据
- Install Docker on Mac OS X(转)
- http://blog.csdn.net/hitmediaman/article/details/6636402
- &ldquo;System.Exception: System.Data.OracleClient 需要 Oracle 客户端软件 8.1.7 或更高版本&rdquo; 的解决方案
- 玩转html5<;canvas>;画图
- HDU 5969 最大的位或 【贪心】 (2016年中国大学生程序设计竞赛(合肥))
- (转载)PHP json_encode() 函数介绍
- 今天进行了一次IOS面试,分享一下面试结果
- 网站引导页flash动画跳转js脚本
- [机器学习] Apriori算法
- VM安装Ubuntu问题合集(无法联网、中文界面设置、中文输入法etc)
- elasticsearch6.6及其插件安装记录(较详细)
- NOIP2013花匠(波动序列)
- Docker Kubernetes 创建管理 Pod
- MySQL(十二)游标和触发器
- 常见的原生javascript DOM操作
- HTML(三)选择器--复杂选择器
- Ubuntu下SSH安装
- 【大数据系列】hadoop单机模式安装