[Bzoj3631][JLOI2014]松鼠的新家 (树上前缀和)
3631: [JLOI2014]松鼠的新家
Time Limit: 10 Sec Memory Limit: 128 MB
Submit: 2350 Solved: 1212
[Submit][Status][Discuss]
Description
Input
Output
Sample Input
Sample Output
HINT
2<= n <=300000
分析:
今天做了noip2015 day2 t3,发现这道省选题竟然是它的简化版。。。。。。。。
道理一样求树上前缀和,以第一个访问的为根,求出dfs序(每个点的st和en)和lca。
对于每一个访问的点u,和前一个点pre在前缀和数组里 +1,他们的lca -2.
这样对于除了根节点以外的所有点,他们的起始位置到结尾位置的和就为那条边经过的次数。(这个用前缀和O(n)处理,每次求一个点只用sum[en] - sum[st - 1]就可以了)。
对于每条边出现次数x,两端的点答案各加x/2,如果为奇数深度更深的那个点答案再加1
根节点最后要加一,最后位置要减1,其实比noip那道题还简单。。。。。
AC代码:
# include <iostream>
# include <cstdio>
# include <cstring>
# include <cstdlib>
# include <algorithm>
using namespace std;
const int N = 3e5 + ;
int head[N],cnt,n,lg,maxn;
int fa[N][],dep[N],vis[N];
struct Edge{
int to,next;
}edge[N << ];
void AddEdge(int u,int v){
Edge E = {v,head[u]};
edge[++cnt] = E;head[u] = cnt;
}
int st[N],en[N];
long long ans[N],sum[N];
void dfs(int u,int pre){
st[u] = ++cnt;
for(int i = head[u];i;i = edge[i].next){
int v = edge[i].to;
if(v == pre)continue;
fa[v][] = u;
dep[v] = dep[u] + ;
dfs(v,u);
}
maxn = max(maxn,dep[u]);
en[u] = cnt;
}
int lca(int x,int y){
if(dep[x] < dep[y])swap(x,y);
for(int i = lg;i >= ;i--){
if(dep[x] - ( << i) >= dep[y])x = fa[x][i];
}
for(int i = lg;i >= ;i--){
if((dep[x] - ( << i)) && fa[x][i] != fa[y][i]){
x = fa[x][i];
y = fa[y][i];
}
}
if(x != y)x = fa[x][];
return x;
}
int main(){
scanf("%d",&n);
int x,y,root;
for(int i = ;i <= n;i++){
scanf("%d",&vis[i]);
}
root = vis[];
for(int i = ;i < n;i++){
scanf("%d %d",&x,&y);
AddEdge(x,y);
AddEdge(y,x);
}
cnt = ;
dep[root] = maxn = ;
dfs(root,-);
int pre = root;
for(lg = ;( << lg) <= maxn;lg++);lg--;
for(int j = ;j <= lg;j++){
for(int i = ;i <= n;i++){
fa[i][j] = fa[fa[i][j - ]][j - ];
}
}
for(int i = ;i <= n;i++){
sum[st[vis[i]]]++;sum[st[pre]]++;
sum[st[lca(vis[i],pre)]] -= ;
pre = vis[i];
}
for(int i = ;i <= n;i++){
sum[i] += sum[i - ];
}
long long z;
for(int i = ;i <= n;i++){
z = sum[en[i]] - sum[st[i] - ];
if(z & 1LL){
ans[i]++;
}
ans[i] += z / 2LL;ans[fa[i][]] += z / 2LL;
}
ans[pre]--;ans[root]++;
for(int i = ;i <= n;i++){
printf("%lld\n",ans[i]);
}
}
[Bzoj3631][JLOI2014]松鼠的新家 (树上前缀和)的更多相关文章
- bzoj3631 [JLOI2014]松鼠的新家——树上差分
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3631 树上差分:注意路径的结尾被多算了一次,最后要减去(不能提前减). 代码如下: #inc ...
- BZOJ3631 [JLOI2014]松鼠的新家 【树上差分】
题目 松鼠的新家是一棵树,前几天刚刚装修了新家,新家有n个房间,并且有n-1根树枝连接,每个房间都可以相互到达,且俩个房间之间的路线都是唯一的.天哪,他居然真的住在"树"上.松鼠想 ...
- [BZOJ3631]:[JLOI2014]松鼠的新家(LCA+树上差分)
题目传送门 题目描述: 松鼠的新家是一棵树,前几天刚刚装修了新家,新家有n个房间,并且有n-1根树枝连接,每个房间都可以相互到达,且俩个房间之间的路线都是唯一的.天哪,他居然真的住在“树”上.松鼠想邀 ...
- BZOJ 3631: [JLOI2014]松鼠的新家 树上差分 + LCA
Description 松鼠的新家是一棵树,前几天刚刚装修了新家,新家有n个房间,并且有n-1根树枝连接,每个房间都可以相互到达,且俩个房间之间的路线都是唯一的.天哪,他居然真的住在“树”上.松鼠想邀 ...
- bzoj3631: [JLOI2014]松鼠的新家(树上差分)
题目链接:https://www.lydsy.com/JudgeOnline/problem.php?id=3631 题目大意:给定含有n个顶点的树,给定走遍整棵树顺序的序列a[1],a[2],a[3 ...
- bzoj3631: [JLOI2014]松鼠的新家(LCA+差分)
题目大意:一棵树,以一定顺序走完n个点,求每个点经过多少遍 可以树链剖分,也可以直接在树上做差分序列的标记 后者打起来更舒适一点.. 具体实现: 先求x,y的lca,且dep[x]<dep[y] ...
- BZOJ3631: [JLOI2014]松鼠的新家
传送门 树上的差分优化,很简单的一道题,应该属于NOIP2015TGD2T3的子问题. //BZOJ 3631 //by Cydiater //2016.10.25 #include <iost ...
- bzoj3631[JLOI2014 松鼠的新家 倍增lca+差分
裸的树上差分+倍增lca 每次从起点到终点左闭右开,这就有一个小技巧,要找到右端点向左端点走的第一步,然后差分就好了 #include<cstdio> #include<cstrin ...
- [JLOI2014]松鼠的新家 树上差分
差分 一开始竟然想分情况讨论来差分,然后发现各自情况要分析, 就是为了解决中间节点重复计算的问题, 结果 最后一想,中间重复计算了一次,那我最后减掉不就好了么,,, 那这就是一道差分裸题了(这是唯一不 ...
随机推荐
- 设置QtreeWidget水平滚动条
转载请注明出处:http://www.cnblogs.com/dachen408/p/7552603.html //设置treewidget水平滚动条 ui.treeWidget->header ...
- Bug的分类和管理流程
1.按照严重程度划分 定义:是指Bug对软件质量的破坏程度,即BUG的存在将对软件的功能和性能产生怎样的影响 分类:系统崩溃.严重.一般.次要.建议 2.按优先级划分 定义:表示处理和修正软件缺陷的现 ...
- 查看本机的ip地址
ifconfig可以查看本机的ip地址:inet addr:10.108.104.185
- P2257 YY的GCD (莫比乌斯反演)
题意:求\[\sum_{i=1}^{n}\sum_{j=1}^{m}[gcd(i,j) = prim]\] 题解:那就开始化式子吧!! \[f(d) = \sum_{i=1}^{n}\sum_{j=1 ...
- 16.04 下修改 ssh 默认端口
打开/etc/ssh/ssh_config,在Port指令下追加新的端口设置: Port 8888 即允许通过端口 8888 进行 ssh 访问. 打开/etc/ssh/sshd_config,进行同 ...
- Eclipse启动的时候提示:Failed to load JavaHL Library
版本信息: Eclipse Project Release Notes Release 4.7.3 启动提示: Subclipse talks to Subversion via a Java API ...
- springboot @test 使用
@RunWith(SpringRunner.class) @SpringBootTest(classes = Application.class) public class Springtest { ...
- Ztree 多选,显示勾选的路径
项目要求,需要向后台传递已经勾选的路径,如 l1-a, l1-l3-c,l1-l3-d;(如果是全选状态则只传递全选状态的路径,不传子节点). 具体可以参考jQ Ztree 的 v3.5 版本 Me ...
- mysql多源复制安装
多源复制的意思是多主一从. 多源复制的前提是必须要开启GTID模式. master1 :192.168.1.110 master2 :192.168.1.111 slave :192.168.1.15 ...
- rc-local.service服务启动失败,导致rc.local中的开机启动服务不能启动
chmod +x /etc/rc.d/rc.local 打开/etc/rc.local文件,将启动非后台执行的指令的最后添加 &,以使相关指令后台运行,然后启动服务 systemctl ...