poj 2763(在线LCA+树状数组)
Housewife Wind
Since Jiajia earned enough money, Wind became a housewife.
Their children loved to go to other kids, then make a simple call to
Wind: 'Mummy, take me home!'
At different times, the time needed to walk along a road may
be different. For example, Wind takes 5 minutes on a road normally, but
may take 10 minutes if there is a lovely little dog to play with, or
take 3 minutes if there is some unknown strange smell surrounding the
road.
Wind loves her children, so she would like to tell her children the exact time she will spend on the roads. Can you help her?
Input
in XX Village, q messages to process, and Wind is currently in hut s. n
< 100001 , q < 100001.
The following n-1 lines each contains three integers a, b and
w. That means there is a road directly connecting hut a and b, time
required is w. 1<=w<= 10000.
The following q lines each is one of the following two types:
Message A: 0 u
A kid in hut u calls Wind. She should go to hut u from her current position.
Message B: 1 i w
The time required for i-th road is changed to w. Note that
the time change will not happen when Wind is on her way. The changed can
only happen when Wind is staying somewhere, waiting to take the next
kid.
Output
Sample Input
3 3 1
1 2 1
2 3 2
0 2
1 2 3
0 3
Sample Output
1
3
题意很简单 k为0时:求s到u的距离 k为1时 把第i条边的权值变为w
求a b两点的距离 用LCA 设d[i]为i到根节点的距离 l(a.b)=d[a]+d[b]-2*d[lca(a,b)];(很容易想到)
修改权值的话 我们用L[i],R[i]分别表示在DFS中第一次经过i节点的时间戳和回溯到该点的时间戳
节点u到根节点的距离就是[0,L[u]]的和
对于更新每一条边时 DFS序较大的的节点为i 将l[i]的权值加上一个w R[i]+1的权值减去一个w 这样l{i]-R[i]区间内所有的顶点在求和的时候都加了w
#include<iostream>
#include<cstdio>
#include<cmath>
#include<map>
#include<cstdlib>
#include<vector>
#include<set>
#include<queue>
#include<cstring>
#include<string.h>
#include<algorithm>
typedef long long ll;
typedef unsigned long long LL;
using namespace std;
const int N=+;
int head[N];
int cnt,n;
int vis[N];
int d[N],dp[N][];
struct node{
int to,next,w;
}edge[*N];
int t1,t2;
int pos[N],dep[N],f[N],G[N];
int w[N];
int L[N],R[N];
void init(){
memset(vis,,sizeof(vis));
cnt=;
memset(head,-,sizeof(head));
memset(pos,-,sizeof(pos));
memset(d,,sizeof(d));
t1=t2=;
}
void add(int u,int v,int w){
edge[cnt].to=v;
edge[cnt].w=w;
edge[cnt].next=head[u];
head[u]=cnt++;
}
int lowbit(int x){
return x&-x;
}
void update(int x,int y){
while(x<=n){
d[x]=d[x]+y;
x=x+lowbit(x);
}
}
int sum(int x){
int ans=;
while(x){
ans=ans+d[x];
x=x-lowbit(x);
}
return ans;
}
void init_RMQ(int n){
for(int i=;i<=n;i++)dp[i][]=i;
for(int j=;(<<j)<=n;j++)
for(int i=;i+(<<j)-<=n;i++)
if(dep[dp[i][j-]]<dep[dp[i+(<<j-)][j-]])dp[i][j]=dp[i][j-];
else
dp[i][j]=dp[i+(<<j-)][j-];
//dp[i][j]=min(dp[i][j-1],dp[i+(1<<j-1)][j-1]);
}
int RMQ(int l,int r){
int k=;
while((<<k+)<=r-l+)k++;
if(dep[dp[l][k]]<dep[dp[r-(<<k)+][k]])return dp[l][k];
else
return dp[r-(<<k)+][k];
//return min(dep[dp[l][k]],dep[dp[r-(1<<k)+1][k]]);
}
int lca(int u,int v){
if(pos[u]>pos[v])return f[RMQ(pos[v],pos[u])];
else
return f[RMQ(pos[u],pos[v])];
}
void DFS(int x,int deep){
f[t1]=x;
dep[t1]=deep;
pos[x]=t1++;
L[x]=++t2;
for(int i=head[x];i!=-;i=edge[i].next){
//cout<<4<<endl;
int v=edge[i].to;
if(pos[v]==-){
//cout<<3<<endl;
G[edge[i].w]=v;
DFS(v,deep+);
f[t1]=x;
dep[t1++]=deep;
} }
R[x]=t2;
}
int main(){
int q,s;
while(scanf("%d%d%d",&n,&q,&s)!=EOF){
init();
int u,v,W;
for(int i=;i<n;i++){
scanf("%d%d%d",&u,&v,&W);
add(u,v,i);
add(v,u,i);
w[i]=W;
}
DFS(,);
/*for(int i=1;i<=n;i++){
cout<<L[i]<<" "<<R[i]<<endl;
}
cout<<endl;
for(int i=1;i<=2*n-1;i++)cout<<f[i]<<" ";
cout<<endl;*/
init_RMQ(*n-);
for(int i=;i<n;i++){
update(L[G[i]],w[i]);
update(R[G[i]]+,-w[i]);
}
u=s;
while(q--){
int k;
scanf("%d",&k);
if(k==){
scanf("%d%d",&u,&W);
update(L[G[u]],W-w[u]);
update(R[G[u]]+,-W+w[u]);
w[u]=W;
}
else{
scanf("%d",&v);
printf("%d\n",sum(L[s])+sum(L[v])-*sum(L[lca(s,v)]));
s=v;
}
}
}
return ;
}
poj 2763(在线LCA+树状数组)的更多相关文章
- hdu 6203 ping ping ping(LCA+树状数组)
hdu 6203 ping ping ping(LCA+树状数组) 题意:给一棵树,有m条路径,问至少删除多少个点使得这些路径都不连通 \(1 <= n <= 1e4\) \(1 < ...
- POJ 2763 Housewife Wind(DFS序+LCA+树状数组)
Housewife Wind Time Limit: 4000MS Memory Limit: 65536K Total Submissions: 11419 Accepted: 3140 D ...
- POJ 2352 Stars(树状数组)
Stars Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 30496 Accepted: 13316 Descripti ...
- POJ 3321 Apple Tree (树状数组+dfs序)
题目链接:http://poj.org/problem?id=3321 给你n个点,n-1条边,1为根节点.给你m条操作,C操作是将x点变反(1变0,0变1),Q操作是询问x节点以及它子树的值之和.初 ...
- poj 2828 Buy Tickets(树状数组 | 线段树)
题目链接:poj 2828 Buy Tickets 题目大意:给定N,表示有个人,给定每一个人站入的位置,以及这个人的权值,如今按队列的顺序输出每一个人的权值. 解题思路:第K大元素,非常巧妙,将人入 ...
- poj 2299 Ultra-QuickSort(树状数组求逆序数+离散化)
题目链接:http://poj.org/problem?id=2299 Description In this problem, you have to analyze a particular so ...
- HDU 6203 ping ping ping(dfs序+LCA+树状数组)
http://acm.hdu.edu.cn/showproblem.php?pid=6203 题意: n+1 个点 n 条边的树(点标号 0 ~ n),有若干个点无法通行,导致 p 组 U V 无法连 ...
- poj 2299 Ultra-QuickSort(树状数组求逆序数)
链接:http://poj.org/problem?id=2299 题意:给出n个数,求将这n个数从小到大排序,求使用快排的需要交换的次数. 分析:由快排的性质很容易发现,只需要求每个数的逆序数累加起 ...
- poj 3067 Japan(树状数组求逆序数)
链接:http://poj.org/problem?id=3067 题意:左边有n个城市,右边有m个城市,建k条道路,问有这k条道路中有多少个交点. 分析:将城市按x和y从小到大排序,对于每条道路,求 ...
随机推荐
- mac中显示隐藏文件和.开头的文件
在控制台中执行一下命令,即可在finder中看到此类文件: defaults write com.apple.Finder AppleShowAllFiles YES killall Finder
- JS——百度背景图
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- JS——try catch throw
本例检测输入变量的值.如果值是错误的,会抛出一个异常(错误).catch 会捕捉到这个错误,并显示一段自定义的错误消息: <script> function myFunction() { ...
- C语言保留字
数值变量相关: int float double char long short unsigned signed 储存说明符 const 用于声明常量 static用于限制变量/函数的作用范围等等 e ...
- C# 调用win32API 获取进程句柄 有毛用???
private void button2_Click(object sender, EventArgs e) { Process[] ProceddingCon = Process.GetProces ...
- Spring装配之——JAVA代码装配Bean
首先创建几个普通的JAVA对象,用于测试JAVA代码装配bean的功能. package soundsystemJava; //作为接口 定义了CD播放器对一盘CD所能进行的操作 public int ...
- Python ---- KMP(博文推荐+代码)
既解决完后宫问题(八皇后问题)后,又利用半天的时间完成了著名的“看毛片”算法——KMP.对于初学者来说这绝对是个大坑,非常难以理解. 在此,向提出KMP算法的三位大佬表示诚挚的敬意.!!!牛X!!! ...
- Oracle数据库的自动备份脚本
@echo off echo ================================================ echo Windows环境下Oracle数据库的自动备份脚本 echo ...
- Delphi / Pascal 语法知识干货
********************************************* Pascal.Delph干货 *************************************** ...
- Sort HDU5884(二分+多叉哈夫曼树)
HDU5884 Sort 题意:有n个序列要进行归并,每次归并的代价是两个序列的长度的和,要求最终的代价不能超过规定的T,求在此前提下一次能同时进行归并的序列的个数k. 思路:还是太单纯,看完题目一直 ...