第一次写树剖~

#include<iostream>
#include<cstring>
#include<cstdio>
#define L(u) u<<1
#define R(u) u<<1|1
using namespace std;
const int MAX=;
int t,head[MAX*],next1[MAX*],tov[MAX*],val[MAX*],tot,n;
int fa[MAX],w[MAX],son[MAX],depth[MAX],tot2,size[MAX];
int d[MAX][],tree[MAX*],top[MAX];
char ch[];
inline void swap(int &a,int &b)
{
int t;
t=a;
a=b;
b=t;
}
inline void add(int a,int b,int c)
{
tot++;
next1[tot]=head[a];
head[a]=tot;
tov[tot]=b;
val[tot]=c;
}
inline void dfs1(int k)
{
son[k]=;
size[k]=;
for (int i=head[k];i;i=next1[i])
{
int v=tov[i];
if (v!=fa[k])
{
fa[v]=k;
depth[v]=depth[k]+;
dfs1(v);
son[k]=size[v]<size[son[k]]?son[k]:v;
size[k]+=size[v];
}
}
}
inline void dfs2(int k,int _top)
{
w[k]=++tot2;
top[k]=_top;
if (son[k]!=) dfs2(son[k],_top);//the same _top
for (int i=head[k];i;i=next1[i])
{
int v=tov[i];
if (v!=fa[k]&&v!=son[k])
dfs2(v,v);//the new _top;
}
}
inline void update(int u,int l,int r,int loc,int _value)
{
if (l==loc&&r==loc)
{
tree[u]=_value;
return ;
}
int mid=(l+r)>>;
if (loc<=mid) update(L(u),l,mid,loc,_value);
else update(R(u),mid+,r,loc,_value);
tree[u]=max(tree[R(u)],tree[L(u)]);//pushup
}
void doit()
{
memset(head,,sizeof(head));
memset(depth,,sizeof(depth));
memset(fa,,sizeof(fa));
memset(tree,,sizeof(tree));
tot2=tot=;
scanf("%d",&n);
for (int i=;i<=n-;i++)
{
scanf("%d%d%d",&d[i][],&d[i][],&d[i][]);
add(d[i][],d[i][],d[i][]);
add(d[i][],d[i][],d[i][]);
}
dfs1();
dfs2(,);
for (int i=;i<=n-;i++)
{
if (depth[d[i][]]>depth[d[i][]]) swap(d[i][],d[i][]);//make the higher depth node to map the Edge
update(,,tot2,w[d[i][]],d[i][]); //change the value of the loc->w[d[i][1]]
}
}
inline int query(int u,int l,int r,int l1,int r1)
{
if (l1<=l&&r1>=r) return tree[u];
int mid=(l+r)>>;
if (r1<=mid) return query(L(u),l,mid,l1,r1);
else if (l1>mid) return query(R(u),mid+,r,l1,r1);
else {
return max(query(L(u),l,mid,l1,r1),query(R(u),mid+,r,l1,r1));
}
}
int findans(int va,int vb)
{
int f1,f2,ans;
f1=top[va];
f2=top[vb];
ans=;
while (f1!=f2)//find lca
{
if (depth[f1]<depth[f2])
{
swap(f1,f2);
swap(va,vb);
}
ans=max(ans,query(,,tot2,w[f1],w[va]));//swap make w[f1]<w[f2]
if (f1==f2) return ans;//in the same chain
va=fa[f1];f1=top[va];
}
if (va==vb) return ans;
if (depth[va]>depth[vb]) swap(va,vb);
return max(ans,query(,,tot2,w[son[va]],w[vb]));//the last do the f1=top[va]
}
void read()
{
ch[]='G';
scanf("%s",ch);
}
void work()
{
for (read();ch[]!='D';read())
{
int x,y;
scanf("%d%d",&x,&y);
if (ch[]=='Q') printf("%d\n",findans(x,y));
else update(,,tot2,w[d[x][]],y);
}
}
int main()
{
scanf("%d",&t);
for (int i=;i<=t;i++)
{
doit();
work();
}
}

SPOJ 375 Query on a tree 树链剖分模板的更多相关文章

  1. 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 ...

  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 树链剖分+线段树

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

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

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

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

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

  6. Query on a tree 树链剖分 [模板]

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

  7. Hdu 5274 Dylans loves tree (树链剖分模板)

    Hdu 5274 Dylans loves tree (树链剖分模板) 题目传送门 #include <queue> #include <cmath> #include < ...

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

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

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

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

随机推荐

  1. Java内部DNS查询实现和参数设置

    一.Java内部DNS查询 Java使用域名查询时,用的自己内部的域名实现机制,最后都是交给InetAddress去做DNS解析. 源码分析参考:http://blog.arganzheng.me/p ...

  2. Ubuntu16.04 802.1x 有线连接 输入账号密码,为什么连接不上?

    ubuntu16.04,在网络配置下找到802.1x安全性,输入账号密码,为什么连接不上?   这是系统的一个bug解决办法:假设你有一定的ubuntu基础,首先你先建立好一个不能用的协议,就是按照之 ...

  3. Android 偶遇小问题解决方案集合

    1.Android 如何让EditText不自动获取焦点 解决方案:找一个EditText的父级控件把EditText默认的行为截断了!设置 android:focusable="true& ...

  4. kali 渗透的一些笔记

    kali实战笔记 17:55 2016/7/19 by: _Silvers kali系统安装后的配置及美化安装vmwareToolstar zxvf VMwareTools-sfsfsfasfasfs ...

  5. 比较器:Compare接口与Comparator接口区别与理解

    一.实现Compare接口与Comparator接口的类,都是为了对象实例数组排序的方便,因为可以直接调用 java.util.Arrays.sort(对象数组名称),可以自定义排序规则. 不同之处: ...

  6. ubuntu command

    uninstall software: sudo apt-get purge openjdk*

  7. archlinux中c语言的rpc编程

    参考:http://www.cs.rutgers.edu/~pxk/rutgers/notes/rpc/ 启动rpc服务端会出现 unable to register 这个错误,据说是要启用 port ...

  8. iOS GCD 编程小结

    一.简单介绍 1.GCD简介? 全称是Grand Central Dispatch,可译为“牛逼的中枢调度器” 纯C语言,提供了非常多强大的函数 2.GCD优势 GCD是苹果公司为多核的并行运算提出的 ...

  9. python函数基础 与文件操作

    函数的定义 函数是通过赋值传递的,参数通过赋值传递给函数.def语句将创建一个函数对象并将其赋值给一个变量名,def语句的一般格式如下: def function_name(arg1,arg2[,.. ...

  10. GPS经纬度换算成XY坐标

    ;        }