【题目描述】

一天机房的夜晚,无数人在MC里奋斗着。。。

大家都知道矿产对于MC来说是多么的重要,但由于矿越挖越少,勇士们不得不跑到更远的地方挖矿,但这样路途上就会花费相当大的时间,导致挖矿效率底下。

cjj提议修一条铁路,大家一致同意。

大家都被CH分配了一些任务:

zjmfrank2012负责绘制出一个矿道地图,这个地图包括家(当然这也是一个矿,毕竟不把家掏空我们是不会走的),和无数个矿,所以大家应该可以想出这是一个无向无环图,也就是一棵树。

Digital_T和cstdio负责铺铁路。。所以这里没他们什么事,两位可以劳作去了。

这个时候song526210932和RMB突然发现有的矿道会刷怪,并且怪的数量会发生变化。作为采矿主力,他们想知道从一个矿到另一个矿的路上哪一段会最困难。。。(困难值用zjm的死亡次数表示)。

【输入格式】

输入文件的第一行有一个整数N,代表矿的数量。矿的编号是1到N。

接下来N-1行每行有三个整数a,b,c,代表第i号矿和第j号矿之间有一条路,在初始时这条路的困难值为c。

接下来有若干行,每行是“CHANGE i ti”或者“QUERY a b”,前者代表把第i条路(路按所给顺序从1到M编号)的困难值修改为ti,后者代表查询a到b所经过的道路中的最大困难值。

输入数据以一行“DONE”结束。

【输出格式】

对每个“QUERY”操作,输出一行一个正整数,即最大困难值。

【分析】

实在是让人无语的背景改变,顺便膜拜一下梦迪神牛Orzzzzzzzz。

最基本的树链剖分。

 #include <cstring>
#include <cmath>
#include <cstdio>
#include <iostream>
#include <vector>
const int maxn=+;
using namespace std;
struct Edge
{
int to;//所指向的
int num;//记录边的编号
};
int d[maxn][],edge=,n,root;//用来记录边的属性
int siz[maxn],son[maxn];//子树大小和重儿子
int fa[maxn],dep[maxn],z;//父亲和深度
int w[maxn],top[maxn],tree[maxn];
char str[];
vector<Edge>map[maxn]; inline void init();
inline void work();
inline void dfs(int u);//第一次DFS
inline void addEdge(int u,int v);//加边
inline void make_tree(int u,int tp);//第二次DFS
inline void update(int root,int l,int r,int num,int c);//c是变更值
inline int read();//读入函数
inline int find(int a,int b);
inline int maxi(int root,int l,int r,int l1,int l2); inline void addEdge(int u,int v)
{
edge++;
map[u].push_back((Edge){v,edge});
}
inline void dfs(int u)//第一次dfs
{
int i;
siz[u]=;
son[u]=;
for (i=;i<map[u].size();i++)
{
int v=map[u][i].to;
if (v!=fa[u])
{
fa[v]=u;//更新父亲
dep[v]=dep[u]+;//更新深度
dfs(v);
if (siz[v]>siz[son[u]]) son[u]=v;
siz[u]+=siz[v];
}
}
}
//建树操作
inline void make_tree(int u,int tp)
{
int i;
w[u]=++z;
top[u]=tp;
if (son[u]!=) make_tree(son[u],top[u]);//优先走重儿子
for (i=;i<map[u].size();i++)
{
int v=map[u][i].to;
if (v!=son[u] && v!=fa[u])
make_tree(v,v);
}
}
//修改操作
inline void update(int root,int l,int r,int num,int c)
{
if (num>r || num<l) return;
if (l==r) {tree[root]=c;return;}
int mid=(l+r)/;
//递归修改
update(root*,l,mid,num,c);
update(root*+,mid+,r,num,c);
tree[root]=max(tree[root*],tree[root*+]);
}
inline void init()
{
int i;
scanf("%d",&n);
root=(+n)/;//随机根
fa[root]=z=dep[root]=edge=;
memset(d,,sizeof(d));
memset(tree,,sizeof(tree));
for (i=;i<n;i++)
{
int u,v,w;
scanf("%d%d%d",&u,&v,&w);
d[i][]=u;d[i][]=v;d[i][]=w;
addEdge(u,v);//加无向边
addEdge(v,u);
}
dfs(root);//第一次
make_tree(root,root);
for (i=;i<n;i++)
{
if (dep[d[i][]]>dep[d[i][]]) swap(d[i][],d[i][]);//交换
update(,,z,w[d[i][]],d[i][]);//开始加边
}
return;
}
inline int read()
{
scanf("%s",str);
if (str[]=='D')
return ;
//printf("%s\n",str);
return ;
}
inline int maxi(int root,int l,int r,int l1,int r1)
{
if (l1>r || r1<l) return ;//边界条件
if (l1<=l && r<=r1) return tree[root];
int mid=(l+r)/;
return max(maxi(root*,l,mid,l1,r1),maxi(root*+,mid+,r,l1,r1));
}
//进行从a到b的询问
inline int find(int a,int b)
{
int f1=top[a],f2=top[b],temp=;
while (f1!=f2)//LCA
{
if (dep[f1]<dep[f2])//统一深度
{
swap(f1,f2);
swap(a,b);
}
temp=max(temp,maxi(,,z,w[f1],w[a]));
a=fa[f1];f1=top[a];//向上传递
}
if (a==b) return temp;
if (dep[a]>dep[b]) swap(a,b);
return max(temp,maxi(,,z,w[son[a]],w[b]));
}
inline void work()
{
int a,b;
while (read())
{
scanf("%d%d",&a,&b);
if (str[]=='Q') printf("%d\n",find(a,b));
else update(,,z,w[d[a][]],b);
}
return;
}
int main()
{
//文件操作
freopen("qtree.in","r",stdin);
freopen("qtree.out","w",stdout);
init();//初始化
work();
return ;
}

【COGS1672】难存的情缘的更多相关文章

  1. Cogs 1672. [SPOJ375 QTREE]难存的情缘 LCT,树链剖分,填坑计划

    题目:http://cojs.tk/cogs/problem/problem.php?pid=1672 1672. [SPOJ375 QTREE]难存的情缘 ★★★☆   输入文件:qtree.in  ...

  2. OI总结(垃圾排版就忽略了吧)

    学OI一年了,到现在联赛所需要的知识已经基本学完了.现在,有必要回过头来,总结总结自己一年来学到的知识以及得到的经验教训. 基础 语言基础 C++的语言基础啥的就略了吧. 算法复杂度分析 O:复杂度的 ...

  3. 染色[SDOI2011]

    题目描述 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成颜色c: 2.询问节点a到节点b路径上的颜色段数量(连续相同颜色被认为是同一段),如"11 ...

  4. 「专题总结」LCT入门

    上次xuefeng说我的专题总结(初探插头dp)太不适合入门了,所以这次丢一些题解包以外的东西. 关键是我自己也不会...急需梳理一下思路... (让我口胡数据结构???顺便推广一下全世界最短的lct ...

  5. 「LCT」

    终于在多篇题解和我的个人超常发挥下抄完了lct的所有题,kx死了. 理解 在我看来,实际上lct的板子没有什么考的,更重要的可能是起到一个数据结构的维护作用实际上就是出题人想给你找点乐子. 前几道题都 ...

  6. CodeIgniter(CI)框架中的验证码

    在CodeIgniter框架中,CI本身自带了验证码,但是查看文档的时候,发现: 需要新建一个表,用来存储验证码信息.因为习惯了session存储验证码信息,所以我把我认为比较好看的验证码应用在了CI ...

  7. php表单数据验证类

    非常好用方便的表单数据验证类 <?php //验证类 class Fun{ function isEmpty($val) { if (!is_string($val)) return false ...

  8. 历代诗词咏宁夏注释2_----苍岩道人<登文昌阁>

    登文昌阁[1] 苍岩道人 壮年碌碌走尘埃,此地清幽不肯来. 老去始惊春梦促,韶光易过槿花开.[2] 历朝兴废书千卷,万古忠奸土一堆.[3] 惟爱莎罗歌最好,闲时拍板满斟杯.[4] 注释 [说明]选自& ...

  9. ThinkPHP/Common/extend.php

    <?php // +---------------------------------------------------------------------- // | ThinkPHP [ ...

随机推荐

  1. The Cow Lexicon(dp)

    Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 7290   Accepted: 3409 Description Few k ...

  2. POJ 3180 The Cow Prom(强联通)

    题目大意: 约翰的N(2≤N≤10000)只奶牛非常兴奋,因为这是舞会之夜!她们穿上礼服和新鞋子,别上鲜花,她们要表演圆舞.           只有奶牛才能表演这种圆舞.圆舞需要一些绳索和一个圆形的 ...

  3. 【动态规划】【缩点】NCPC 2014 G Outing

    题目链接: http://acm.csu.edu.cn/OnlineJudge/problem.php?id=1793 题目大意: 一辆公交车,上面M个座位,N个人(M<=N<=1000) ...

  4. 【KMP】【最小表示法】NCPC 2014 H clock pictures

    题目链接: http://acm.csu.edu.cn/OnlineJudge/problem.php?id=1794 题目大意: 两个无刻度的钟面,每个上面有N根针(N<=200000),每个 ...

  5. 【最短路】BAPC2014 B Button Bashing (Codeforces GYM 100526)

    题目链接: http://codeforces.com/gym/100526 http://acm.hunnu.edu.cn/online/?action=problem&type=show& ...

  6. Uncle Sam 山姆大叔

    山姆大叔被用来代指“美国”或“美国政府”,主要在美国.英国,尤其是在新闻界中使用较多.“山姆大叔”是美国的绰号,它同自由女神一样,为世人所熟知. 形象 美国的报纸杂志.文学作品和漫画中,经常可以看到“ ...

  7. [jAudio] JAVA上经典特征提取工具

    1.下载Jar包后引入 现在的问题是jAudio通常是给人UI进行操作的,直接使用怎么办? 看了源码,发现特征提取是通过类之间交叉调用实现的,是否有办法整合一下?

  8. Codeforces Round #324 (Div. 2)解题报告

    ---恢复内容开始--- Codeforces Round #324 (Div. 2) Problem A 题目大意:给二个数n.t,求一个n位数能够被t整除,存在多组解时输出任意一组,不存在时输出“ ...

  9. SRM 392(1-250pt)

    DIV1 250pt 题意:给两个各含有一个*号的字符串s1和s2,可以用一个任意字符串代替*号(注意是串,不是只能用单个字符代替,也可以为用空串代替),问能否将s1和s2变为相同的字符串.如果能输出 ...

  10. 理解RESTful架构(转)

    理解RESTful架构   作者: 阮一峰 http://www.ruanyifeng.com/blog/2011/09/restful 越来越多的人开始意识到,网站即软件,而且是一种新型的软件. 这 ...