Codeforces 191C (LCA+树上差分算法)
题面
传送门
题目大意:
给出一棵树,再给出k条树上的简单路径,求每条边被不同的路径覆盖了多少次
分析
解决这个问题的经典做法是树上差分算法
它的思想是把”区间”修改转化为左右端点的修改
在树上,每个节点初始权值为0,对于每条路径(x,y),我们令节点x的权值+1,节点y的权值-1,节点LCA(x,y)的权值-2
最后进行一次DFS,求出F[x]表示x为根的子树中各节点的权值之和,F[x]就是x与它的父节点之间的树边被覆盖的次数
用dfs序+ST表求LCA,时间复杂度O(nlog2n+k)" role="presentation" style="position: relative;">O(nlog2n+k)O(nlog2n+k)
代码
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#define maxn 100005
#define maxlog 32
using namespace std;
int n,k;
struct edge{
int from;
int to;
int next;
int index;
}E[maxn*2];
int head[maxn];
int size=0;
void add_edge(int u,int v,int id){
size++;
E[size].from=u;
E[size].to=v;
E[size].next=head[u];
E[size].index=id;
head[u]=size;
}
int dfn[maxn*2];
int used[maxn];
int fipos[maxn*2];
int deep[maxn*2];
int st[maxn*4][maxlog];
int cnt=0;
void get_dfn(int u,int d){
dfn[++cnt]=u;
if(fipos[u]==0){
fipos[u]=cnt;
deep[u]=cnt;
}
used[u]=1;
for(int i=head[u];i;i=E[i].next){
if(!used[E[i].to]){
get_dfn(E[i].to,d+1);
dfn[++cnt]=u;
}
}
}
void st_init(){
for(int i=1;i<=(n-1)*2;i++){
st[i][0]=dfn[i];
}
for(int j=1;(1<<j)<=(n-1)*2;j++){
for(int i=1;i<=(n-1)*2;i++){
if(deep[st[i][j-1]]<deep[st[i+(1<<(j-1))][j-1]]) st[i][j]=st[i][j-1];
else st[i][j]=st[i+(1<<(j-1))][j-1];
}
}
}
int st_query(int l,int r){
if(l>r) swap(l,r);
int k=log2(r-l+1);
if(deep[st[l][k]]<deep[st[r-(1<<k)+1][k]]) return st[l][k];
else return st[r-(1<<k)+1][k];
}
int lca(int x,int y){
int fx=fipos[x];
int fy=fipos[y];
return st_query(fx,fy);
}
int len[maxn];
int outlen[maxn];//按题目顺序输出
void get_len(int u){
used[u]=1;
for(int i=head[u];i;i=E[i].next){
if(!used[E[i].to]){
get_len(E[i].to);
len[u]+=len[E[i].to];
outlen[E[i].index]+=len[E[i].to];
}
}
}
int main(){
int u,v;
scanf("%d",&n);
for(int i=1;i<=n-1;i++){
scanf("%d %d",&u,&v);
add_edge(u,v,i);
add_edge(v,u,i);
}
get_dfn(1,0);
st_init();
scanf("%d",&k);
for(int i=1;i<=k;i++){
scanf("%d %d",&u,&v);
//树上差分算法
len[u]++;
len[v]++;
len[lca(u,v)]-=2;
}
memset(used,0,sizeof(used));
get_len(1);
for(int i=1;i<=n-1;i++) printf("%d ",outlen[i]);
}
Codeforces 191C (LCA+树上差分算法)的更多相关文章
- [BZOJ3307]:雨天的尾巴(LCA+树上差分+权值线段树)
题目传送门 题目描述: N个点,形成一个树状结构.有M次发放,每次选择两个点x,y对于x到y的路径上(含x,y)每个点发一袋Z类型的物品.完成所有发放后,每个点存放最多的是哪种物品. 输入格式: 第一 ...
- P1600 天天爱跑步[桶+LCA+树上差分]
题目描述 小c同学认为跑步非常有趣,于是决定制作一款叫做<天天爱跑步>的游戏.<天天爱跑步>是一个养成类游戏,需要玩家每天按时上线,完成打卡任务. 这个游戏的地图可以看作一一棵 ...
- [luogu P3128][USACO15DEC]Max Flow [LCA][树上差分]
题目描述 Farmer John has installed a new system of pipes to transport milk between the stalls in his b ...
- bzoj4326 树链剖分 + 线段树 // 二分 lca + 树上差分
https://www.lydsy.com/JudgeOnline/problem.php?id=4326 题意:N个点的树上给M条树链,问去掉一条边的权值之后所有树链长度和的最大值最小是多少. 首先 ...
- 2018.08.22 codves2370 小机房的树(lca+树上差分)
传送门 一道板子题. 直接树链剖分维护树上lca然后差分就行了. 代码: #include<bits/stdc++.h> #define N 50005 #define lc (p< ...
- 【洛谷】【lca+树上差分】P3258 [JLOI2014]松鼠的新家
[题目描述:] 松鼠的新家是一棵树,前几天刚刚装修了新家,新家有n(2 ≤ n ≤ 300000)个房间,并且有n-1根树枝连接,每个房间都可以相互到达,且俩个房间之间的路线都是唯一的.天哪,他居然真 ...
- [JLOI2014] 松鼠的新家 (lca/树上差分)
[JLOI2014]松鼠的新家 题目描述 松鼠的新家是一棵树,前几天刚刚装修了新家,新家有n个房间,并且有n-1根树枝连接,每个房间都可以相互到达,且俩个房间之间的路线都是唯一的.天哪,他居然真的住在 ...
- LOJ2425 NOIP2015 运输计划 【二分+LCA+树上差分】*
LOJ2425 NOIP2015 运输计划 LINK 题意:给你一颗树,可以将任意一条边的权值变成0,然后求m条路径的长度的最小值 思路: 先二分最后的距离ans,然后我们把路程大于ans的所有路径拿 ...
- poj3417 Network——LCA+树上差分
题目:http://poj.org/problem?id=3417 根据一条边被几个环覆盖来判断能不能删.有几种情况等: 用树上差分,终点 s++,LCA s-=2,统计时计算子树s值的和即可: 用S ...
随机推荐
- HTML5 入门基础
HTML5概述HTML5於2004年被WHATWG(网页超文本技术工作小组)提出,於2007年被W3C接纳.在2008年1月22日,第一份正式草案已公布.WHATWG表示该规范是目前正在进行的工作,仍 ...
- QQ输入法用户评价
1.用户界面 用户界面简洁,并且可以随用户喜好自己更换,人性化,优化性比较大 2.记住用户选择 当输入一个字时,下一次输入这个拼音第一位的字就是上一次,或者使用次数最多的字.假如所使用的的字在后边,输 ...
- sqlserver数据库脱机和分离的区别
脱机和分离的区别: 分离和脱机都可以使数据库不能再被使用,但是分离后需要附加才能使用,而脱机后只需联机就可以用了. 附加数据库报错: 无法打开物理文件 XXX.mdf".操作系统错误 5:& ...
- 对npm的认识
npm由三个不同的组件组成:1,网站 2.命令行界面(CLI)3.注册表 需要在网站注册 命令行界面用来进行交互 注册表来进行保存 安装本地软件包 npm install 包名 更新本地软件包 npm ...
- jzoj6404. 【NOIP2019模拟11.04】B
题目描述 Description Input 从文件b.in中读入数据. 第丬行三个正整数 n, m, K. 接下来 n 行每行 m 个正整数, 表示矩阵A. Output 输出到文件b.out中. ...
- docker 内时区和宿主机差8个小时,怎么办?
docker run -d -it --name tt -e TZ=Asia/Shanghai -p : api 使用-e参数指定时区
- Android开发实践:Android.mk模板
关于Android NDK开发的文章已经比较多了,我的博客中也分享了很多NDK开发相关经验和技巧,今天简单写了一个 Android.mk 的示例模板,供初学者参考. 本模板主要给大家示例 Androi ...
- BZOJ 1733: [Usaco2005 feb]Secret Milking Machine 神秘的挤奶机 网络流 + 二分答案
Description Farmer John is constructing a new milking machine and wishes to keep it secret as long a ...
- vue.js条件渲染 v-if else-if v-for
v-if: 在字符串模板中,如 Handlebars ,我们得像这样写一个条件块: {{#if ok}} <!-- Handlebars 模板 --> <h1>Yes</ ...
- 转: Github上关于iOS的各种开源项目集合
https://blog.csdn.net/jiashaoying/article/details/79079500 下拉刷新 EGOTableViewPullRefresh - 最早的下拉刷新控件. ...