用每个点代表父节点到此点的边。建立一一映射后就可以用点权的方法处理了。

注意的是路径两端节点的处理

 #include <cstdio>
#include <algorithm>
#include <vector> using namespace std; const int maxn = 1e5+;
int val[maxn],dep[maxn],siz[maxn],top[maxn],id[maxn],son[maxn],fa[maxn];
int topw,M; vector<int> G[maxn];
struct Edge{
int x,y,val;
}e[maxn]; void dfs_1(int u,int f,int d)
{
fa[u] = f;
son[u] = ;
siz[u] = ;
dep[u] = d; for(int i=;i<G[u].size();i++) if(G[u][i] != f )
{
dfs_1(G[u][i],u,d+);
siz[u] += siz[G[u][i]];
if(siz[son[u] ] < siz[G[u][i] ])
{
son[u] = G[u][i];
}
}
} void dfs_2(int u,int tp)
{
top[u] = tp;
id[u] = ++topw;
if(son[u]) dfs_2(son[u],tp);
for(int i=;i<G[u].size();i++) if(G[u][i] != fa[u] && G[u][i] != son[u])
{
dfs_2(G[u][i],G[u][i]);
}
} int N,T; void debug()
{
for(int i=;i<=N;i++)
{
printf("%d siz:%d son:%d dep:%d fa:%d ",i,siz[i],son[i],dep[i],fa[i]);
printf("top:%d id:%d\n",top[i],id[i]);
}
} /*-------------------------------------*/
//segment Tree
#define lson(x) (x<<1)
#define rson(x) (x<<1|1) struct SegmentTree{
int l,r,val;
}sgtree[*maxn]; void pushup(int x)
{
sgtree[x].val = max(sgtree[lson(x)].val,sgtree[rson(x)].val);
} void Build(int l,int r,int x)
{
sgtree[x].l = l;
sgtree[x].r = r;
if(l==r)
{
sgtree[x].val = val[l];
return ;
}
int mid = (l+r)>>;
Build(l,mid,lson(x));
Build(mid+,r,rson(x));
pushup(x);
} void update(int x,int v,int add)
{
if(sgtree[x].l == sgtree[x].r)
{
sgtree[x].val = add;
//printf("change:%d %d\n",v,sgtree[x].l);
return ;
}
int mid = (sgtree[x].l+sgtree[x].r)>>;
if(v <= mid) update(lson(x),v,add);
else update(rson(x),v,add);
pushup(x);
} int query(int x,int l,int r)
{
if(sgtree[x].l >= l && sgtree[x].r <= r)
{
return sgtree[x].val;
}
int mid = (sgtree[x].l+sgtree[x].r)>>;
int ans = ;
if(l <= mid) ans = max(ans,query(lson(x),l,r));
if(r > mid) ans = max(ans,query(rson(x),l,r));
return ans;
} int Find(int u,int v)
{
int ans = ,fu = top[u],fv = top[v];
while(fu != fv)
{
if(dep[fu] < dep[fv])
{
swap(fu,fv);swap(u,v);
}
ans = max(ans,query(,id[fu],id[u]));
u = fa[fu];
fu = top[u];
}
if(u == v) return ans;
if(dep[u]>dep[v]) swap(u,v);
return max(ans,query(,id[son[u] ],id[v]));
} int main()
{
//freopen("input.in","r",stdin);
scanf("%d",&T);
while(T--)
{
scanf("%d",&N);
for(int i=,a,b,c;i<N;i++)
{
scanf("%d%d%d",&a,&b,&c);
e[i].x = a;
e[i].y = b;
e[i].val = c;
G[a].push_back(b);
G[b].push_back(a);
}
topw = ;
dfs_1(,,);
dfs_2(,);
//debug(); for(int i=;i<N;i++)
{
if(dep[e[i].x] < dep[e[i].y]) swap(e[i].x,e[i].y);
val[id[e[i].x]] = e[i].val;
} Build(,topw,);
char op[];
while(scanf("%s",op) && op[] != 'D')
{
int a,b;
scanf("%d%d",&a,&b);
if(op[] == 'Q')
printf("%d\n",Find(a,b));
else if(op[] == 'C')
update(,id[e[a].x],b);
} for(int i=;i<=N;i++) G[i].clear();
}
}

SPOJ QTREE-Query on a tree-树链剖分-边权的更多相关文章

  1. SPOJ QTREE Query on a tree 树链剖分+线段树

    题目链接:http://www.spoj.com/problems/QTREE/en/ QTREE - Query on a tree #tree You are given a tree (an a ...

  2. spoj QTREE - Query on a tree(树链剖分+线段树单点更新,区间查询)

    传送门:Problem QTREE https://www.cnblogs.com/violet-acmer/p/9711441.html 题解: 树链剖分的模板题,看代码比看文字解析理解来的快~~~ ...

  3. SPOJ QTREE Query on a tree ——树链剖分 线段树

    [题目分析] 垃圾vjudge又挂了. 树链剖分裸题. 垃圾spoj,交了好几次,基本没改动却过了. [代码](自带常数,是别人的2倍左右) #include <cstdio> #incl ...

  4. SPOJ QTREE Query on a tree --树链剖分

    题意:给一棵树,每次更新某条边或者查询u->v路径上的边权最大值. 解法:做过上一题,这题就没太大问题了,以终点的标号作为边的标号,因为dfs只能给点分配位置,而一棵树每条树边的终点只有一个. ...

  5. spoj 375 QTREE - Query on a tree 树链剖分

    题目链接 给一棵树, 每条边有权值, 两种操作, 一种是将一条边的权值改变, 一种是询问u到v路径上最大的边的权值. 树链剖分模板. #include <iostream> #includ ...

  6. spoj 375 Query on a tree (树链剖分)

    Query on a tree You are given a tree (an acyclic undirected connected graph) with N nodes, and edges ...

  7. SPOJ 375 Query on a tree 树链剖分模板

    第一次写树剖~ #include<iostream> #include<cstring> #include<cstdio> #define L(u) u<&l ...

  8. POJ3237 Tree 树链剖分 边权

    POJ3237 Tree 树链剖分 边权 传送门:http://poj.org/problem?id=3237 题意: n个点的,n-1条边 修改单边边权 将a->b的边权取反 查询a-> ...

  9. SPOJ Query on a tree 树链剖分 水题

    You are given a tree (an acyclic undirected connected graph) with N nodes, and edges numbered 1, 2, ...

  10. Query on a tree——树链剖分整理

    树链剖分整理 树链剖分就是把树拆成一系列链,然后用数据结构对链进行维护. 通常的剖分方法是轻重链剖分,所谓轻重链就是对于节点u的所有子结点v,size[v]最大的v与u的边是重边,其它边是轻边,其中s ...

随机推荐

  1. 使用 $(function(){}) 时遇到的一个小bug及解决方法

    在 $(function(){}) 中声明函数,在 $(function(){}) 外调函数,会报错 原因: 页面加载后,会先执行 $(function(){}) 外面的语句,再执行 $(functi ...

  2. flask使用基础

    1.安装 pip install Flask 基本依赖库: jinja2:实现对模板的处理 werkzeug:本质是socket服务器,用于接收http请求,并对请求进行预处理,然后触发Flaks框架 ...

  3. 重装mysql后导致Navicat连接失败

    今天重装了mysql数据库,然后再使用navicat去连接数据库的时候,一直报错 1251 Client does not support authentication protocol reques ...

  4. hdu 1730 Nim博弈

    题目来源:http://acm.hdu.edu.cn/showproblem.php?pid=1730 Nim博弈为:n堆石子,每个人可以在任意一堆中取任意数量的石子 n个数异或值为0就后手赢,否则先 ...

  5. 如何实现用将富文本编辑器内容保存为txt文件并展示

    1.实现思路 创建一个xx.txt文件,存放于项目路径下 用文件流去读取文件内容并将读取的内容存放到页面的富文本编辑器框内 富文本编辑框内容改变后,保存时用文件流的方式保存到xx.txt文件中 提示: ...

  6. mysql常用命令行操作(一):登陆、退出、查看端口、修改密码、刷新

    一.登陆和退出mysql mysql -u root -p # 登陆exit # 退出 二.查看当前mysql的端口号 show global variables like 'port'; 三.查看用 ...

  7. UnicodeEncodeError: 'ascii' codec can't encode characters in position 0-25: ordinal not in range(128)

    python报错:UnicodeEncodeError: 'ascii' codec can't encode characters in position 0-25: ordinal not in ...

  8. 测试工具之ab

    ab命令原理  Apache的ab命令模拟多线程并发请求,测试服务器负载压力,也可以测试nginx.lighthttp.IIS等其它Web服务器的压力.  ab命令对发出负载的计算机要求很低,既不会占 ...

  9. linux之常见错误

    在日常开发中,尤其是在Linux中进行操作的时候,经常会碰到各种各样的错误.记录一下,熟能生巧,慢慢参透linux的奥秘 1) 在安装ssl证书的时候,发生certbot命令无法使用的情况 解决方案: ...

  10. java.util.Collections.copy():列表List浅拷贝

    今天同事问我怎样将一个列表(list1)拷贝到另一个列表(list2),然后修改新的列表(list2)不会影响到旧的列表(list1),想了一想,这是深拷贝啊. 可是,除了循环new还有别的办法吗,想 ...