题目连接:http://acm.hust.edu.cn/vjudge/contest/view.action?cid=28982#problem/I

题意:一棵包含N 个结点的树,每条边都有一个权值,要求模拟两种操作:

(1)改变某条边的权值。

(2)询问U,V 之间的路径中权值最大的边。

树链剖分裸题,入门资料:http://blog.sina.com.cn/s/blog_6974c8b20100zc61.html

#include <cstdio>
#include <cstring>
#include <string>
#include <cmath>
#include <iostream>
#include <algorithm>
#include <queue>
#include <cstdlib>
#include <stack>
#include <vector>
#include <set>
#include <map>
#define LL long long
#define mod 10007
#define inf 0x3f3f3f3f
#define N 10010
#define FILL(a,b) (memset(a,b,sizeof(a)))
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
using namespace std;
struct edge
{
int to,next;
edge(){}
edge(int to,int next):to(to),next(next){}
}e[N<<];
int head[N<<],tot;
int top[N];//top[v]表示v所在的重链的顶端节点
int fa[N];//父亲节点
int dep[N];//深度
int sz[N];//si[v]表示以v为根节点的子树的节点数
int son[N];//重儿子
int p[N];//p[v]表示v与其父亲节点的连边在线段树中的位置
int fp[N];//与p数组相反
int pos;//所有链构成的线段树总长度
int mx[N<<],E[N][];
void addedge(int u,int v)
{
e[tot]=edge(v,head[u]);
head[u]=tot++;
}
void init()
{
tot=;FILL(head,-);
pos=;FILL(son,-);
}
void dfs(int u,int f,int d)
{
sz[u]=;dep[u]=d;fa[u]=f;
for(int i=head[u];~i;i=e[i].next)
{
int v=e[i].to;
if(v==f)continue;
dfs(v,u,d+);
sz[u]+=sz[v];
if(son[u]==-||sz[son[u]]<sz[v])son[u]=v;
}
}
void getpos(int u,int sp)
{
top[u]=sp;
p[u]=++pos;
fp[pos]=u;
if(son[u]==-)return;
getpos(son[u],sp);
for(int i=head[u];~i;i=e[i].next)
{
int v=e[i].to;
if(v!=son[u]&&v!=fa[u])
{
getpos(v,v);
}
}
}
int Pushup(int rt)
{
mx[rt]=max(mx[rt<<],mx[rt<<|]);
}
void update(int id,int c,int l,int r,int rt)
{
if(l==r)
{
mx[rt]=c;
return;
}
int m=(l+r)>>;
if(id<=m)update(id,c,lson);
else update(id,c,rson);
Pushup(rt);
}
int query(int L,int R,int l,int r,int rt)
{
if(L<=l&&r<=R)
return mx[rt];
int m=(l+r)>>;
int res=-inf;
if(L<=m)res=max(res,query(L,R,lson));
if(m<R)res=max(res,query(L,R,rson));
return res;
}
int lca(int u,int v)
{
int fu=top[u],fv=top[v];
int res=-inf;
while(fu!=fv)
{
if(dep[fu]<dep[fv])
{
swap(fu,fv);swap(u,v);
}
res=max(res,query(p[fu],p[u],,pos,));
u=fa[fu];fu=top[u];
}
if(u==v)return res;
if(dep[u]>dep[v])swap(u,v);
return max(res,query(p[son[u]],p[v],,pos,));
}
int main()
{
int T,n,u,v;
scanf("%d",&T);
while(T--)
{
init();
scanf("%d",&n);
for(int i=;i<n;i++)
{
scanf("%d%d%d",&E[i][],&E[i][],&E[i][]);
addedge(E[i][],E[i][]);
addedge(E[i][],E[i][]);
}
dfs(,,);
getpos(,);
for(int i=;i<n;i++)
{
if(dep[E[i][]]>dep[E[i][]])
swap(E[i][],E[i][]);
update(p[E[i][]],E[i][],,pos,);
}
char op[];
while()
{
scanf("%s",op);
if(op[]=='D')break;
scanf("%d%d",&u,&v);
if(op[]=='Q')
printf("%d\n",lca(u,v));
else update(p[E[u][]],v,,pos,);
}
}
}

SPOJ 375(树链剖分)的更多相关文章

  1. SPOJ 375 树链剖分

    SPOJ太慢了,SPOJ太慢了, 题意:给定n(n<=10000)个节点的树,每条边有边权,有两种操作:1.修改某条变的边权:2.查询u,v之间路径上的最大边权. 分析:树链剖分入门题,看这里: ...

  2. SPOJ 375 (树链剖分 - 边权剖分 - 修改单边权)

    题目链接:http://acm.hust.edu.cn/vjudge/contest/view.action?cid=28982#problem/I 给你一棵有边权的树,有两个操作:一个操作是输出l到 ...

  3. SPOJ 375 (树链剖分+线段树)

    题意:一棵包含N 个结点的树,每条边都有一个权值,要求模拟两种操作:(1)改变某条边的权值,(2)询问U,V 之间的路径中权值最大的边. 思路:最近比赛总是看到有树链剖分的题目,就看了论文,做了这题, ...

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

    人生第一道树链剖分的题目,其实树链剖分并不是特别难. 思想就是把树剖成一些轻链和重链,轻链比较少可以直接修改,重链比较长,用线段树去维护. 貌似大家都是从这篇博客上学的. #include <c ...

  5. spoj 375 树链剖分模板

    /* 只是一道树链刨分的入门题,作为模板用. */ #include<stdio.h> #include<string.h> #include<iostream> ...

  6. spoj 375 树链剖分 模板

    QTREE - Query on a tree #tree You are given a tree (an acyclic undirected connected graph) with N no ...

  7. SPOJ QTREE 树链剖分

    树链剖分的第一题,易懂,注意这里是边. #include<queue> #include<stack> #include<cmath> #include<cs ...

  8. Spoj Query on a tree SPOJ - QTREE(树链剖分+线段树)

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

  9. 【学术篇】SPOJ QTREE 树链剖分

    发现链剖这东西好久不写想一遍写对是有难度的.. 果然是熟能生巧吧.. WC的dalao们都回来了 然后就用WC的毒瘤题荼毒了我们一波, 本来想打个T1 44分暴力 然后好像是特判写挂了还是怎么的就只能 ...

  10. spoj 375 Query on a tree(树链剖分,线段树)

      Query on a tree Time Limit: 851MS   Memory Limit: 1572864KB   64bit IO Format: %lld & %llu Sub ...

随机推荐

  1. 解决php下多人同时操作数据表

    当同一时刻,多人对同一个表进行insert或者update的时候,往往会出现同一条数据出现好多次或者一些奇怪的问题,可以通过mysql的锁表机制来进行排队解决这个问题 php中插入数据之前锁表 // ...

  2. 创建webservice 用service.xml配置(复杂点的方法)

    用Axis2实现Web Service,虽然可以将POJO类放在axis2/WEB-INF/pojo目录中直接发布成Web Service,这样做不需要进行任何配置,但这些POJO类不能在任何包中.这 ...

  3. oracle批量插入数据

    有一次开发一个功能,须要导入别人提供的几万条数据, 数据在一个*.sql文件里,大概有8万条数据 insert into testtable(id,name) values(1,'1')   ---- ...

  4. html-图片button,抓包---Shinepans

    askLike.html <html> <meta http-equiv="content-type" content="text/html;chars ...

  5. Java字符串找出4个字节长度的字符

    不解释,直接上代码:  由于Iteye代码贴四个字节的UTF-8字符出错,特能图的方式发布几个特殊字符:  public class Byte4Check { public static void m ...

  6. 中文分词算法之最大正向匹配算法(Python版)

    最大匹配算法是自然语言处理中的中文匹配算法中最基础的算法,分为正向和逆向,原理都是一样的. 正向最大匹配算法,故名思意,从左向右扫描寻找词的最大匹配. 首先我们可以规定一个词的最大长度,每次扫描的时候 ...

  7. Problem B: Ternarian Weights

    大致题意:使用三进制砝码采取相应的措施衡量出给定的数字主要思路:三进制,如果 大于 2 向前进位,之前一直没写好放弃了,这次终于写好了…… #include <iostream> #inc ...

  8. .htaccess和license文件编写

    1 .htaccess 1.1 文件的位置 默认情况下放置于根目录 1.2 .htaccess文件的编写 1.2.1 错误页面跳转 ErrorDocument + 错误码 + 跳转路径/提示文字 eg ...

  9. Android菜鸟的成长笔记(12)——Handler、Loop、MessageQueue

    原文:[置顶] Android菜鸟的成长笔记(12)——Handler.Loop.MessageQueue 当一个程序第一次启动时,Android会启动一条主线程(Main Thread),主线程主要 ...

  10. Swift - 判断设备类型开发兼容的iOS应用(iPad使用分隔视图控制器)

    1,分割视图控制器(UISplitViewController) 在iPhone应用中,使用导航控制器由上一层界面进入下一层界面. 但iPad屏幕较大,通常使用SplitViewController来 ...