• 题目大意

    有n座小岛,当中每一个岛都有若干帝企鹅。

    一開始岛与岛之间互不相连。有m个操作。各自是在两个岛之间修一座双向桥,若两岛已连通则不修并输出no,若不连通就输出yes并修建。改动一个岛上帝企鹅的数量;询问从岛A到岛B可看到多少帝企鹅,若到不了输出impossible。

  • 题解

    继续试水LCT。LCT维护每一个点自身的企鹅数以及其在Splay下的子树的企鹅数的总和。

    修桥操作要在LCT中询问是否有同样的根,没有则添边。改动时把要被改动的点弄到树根去,直接改动就可以。查询时要先推断是否为同一结点,再推断是否连通。若连通,则把当中一个点x弄到根上,还有一个点y用access连上去,再用Splay把y弄到辅助树的根上。

    这时x一定是y最左端的子孙(由于它是根。中序序列里最靠前)。直接输出y左子树企鹅的总和加上y自己的企鹅数就可以。

  • Code

#include <cstdio>
#include <algorithm>
#include <cstring>
#define maxn 30005
using namespace std;
int n, m;
struct node *nil, *T[maxn], *S[maxn];
struct node
{
bool rev;
int val, s;
node *fa, *lc, *rc;
node(bool rev = false, int val = 0, int s = 0, node *fa = nil, node *lc = nil, node *rc = nil)
: rev(rev), val(val), s(s), fa(fa), lc(lc), rc(rc) {}
inline void update()
{
s = lc -> s + rc -> s + val;
}
inline void rever()
{
rev ^= 1;
swap(lc, rc);
}
inline void pushdown()
{
if(rev)
{
rev = false;
lc -> rever(); rc -> rever();
}
}
};
inline void zig(node *x)
{
node *y = x -> fa;
y -> lc = x -> rc;
x -> rc -> fa = y;
x -> rc = y;
x -> fa = y -> fa;
if(y == y -> fa -> lc) y -> fa -> lc = x;
else if(y == y -> fa -> rc) y -> fa -> rc = x;
y -> fa = x;
y -> update();
}
inline void zag(node *x)
{
node *y = x -> fa;
y -> rc = x -> lc;
x -> lc -> fa = y;
x -> lc = y;
x -> fa = y -> fa;
if(y == y -> fa -> lc) y -> fa -> lc = x;
else if(y == y -> fa -> rc) y -> fa -> rc = x;
y -> fa = x;
y -> update();
}
void splay(node *x)
{
int top = 0;
S[top++] = x;
for(node *i = x; i == i -> fa -> lc || i == i -> fa -> rc; i = i -> fa)
{
S[top++] = i -> fa;
}
while(top--) S[top] -> pushdown();
node *y = nil, *z = nil;
while(x == x -> fa -> lc || x == x -> fa -> rc)
{
y = x -> fa; z = y -> fa;
if(x == y -> lc)
{
if(y == z -> lc) zig(y);
zig(x);
}
else
{
if(y == z -> rc) zag(y);
zag(x);
}
}
x -> update();
}
inline void access(node *x)
{
for(node *y = nil; x != nil; y = x, x = x -> fa)
{
splay(x);
x -> rc = y;
x -> update();
}
}
inline void makeroot(node *x)
{
access(x); splay(x); x -> rever();
}
inline void lnk(node *x, node *y)
{
makeroot(x);
x -> fa = y;
splay(y);
}
inline node* find(node *x)
{
access(x); splay(x);
while(x -> lc != nil) x = x -> lc;
return x;
}
inline void change(node *x, int k)
{
makeroot(x);
x -> val = k;
x -> update();
}
inline int query(node *x, node *y)
{
if(x == y) return x -> val;
if(find(x) != find(y)) return -1;
makeroot(x);
access(y);
splay(y);
return (y -> lc -> s + y -> val);
}
int main()
{
int a, b, c;
char ch[10];
scanf("%d", &n);
nil = new node(); *nil = node();
for(int i = 1; i <= n; ++i) T[i] = new node();
for(int i = 1; i <= n; ++i)
{
scanf("%d", &(T[i] -> val));
T[i] -> update();
}
scanf("%d", &m);
while(m--)
{
scanf("%s%d%d", ch, &a, &b);
if(ch[0] == 'b')
{
if(find(T[a]) != find(T[b]))
{
lnk(T[a], T[b]); puts("yes");
}
else puts("no");
}
else if(ch[0] == 'p')
{
change(T[a], b);
}
else
{
c = query(T[a], T[b]);
if(c == -1) puts("impossible");
else printf("%d\n", c);
}
}
for(int i = 1; i <= n; ++i)
{
delete T[i];
T[i] = NULL;
}
delete nil;
nil = NULL;
return 0;
}

bzoj2843极地旅行社题解的更多相关文章

  1. bzoj2843极地旅行社

    bzoj2843极地旅行社 题意: 一些点,每个点有一个权值.有三种操作:点与点连边,单点修改权值,求两点之间路径上点的权值和(需要判输入是否合法) 题解: 以前一直想不通为什么神犇们的模板中LCT在 ...

  2. BZOJ2843: 极地旅行社

    2843: 极地旅行社 Time Limit: 10 Sec  Memory Limit: 256 MBSubmit: 90  Solved: 56[Submit][Status] Descripti ...

  3. BZOJ2843 极地旅行社 LCT

    欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ2843 题意概括 有n座岛 每座岛上的企鹅数量虽然会有所改变,但是始终在[0, 1000]之间.你的 ...

  4. BZOJ2843——极地旅行社

    1.题目大意:动态树问题,点修改,链查询.另外说明双倍经验题=bzoj1180 2.分析:lct模板题,练手的 #include <stack> #include <cstdio&g ...

  5. BZOJ2843极地旅行社&BZOJ1180[CROATIAN2009]OTOCI——LCT

    题目描述 给出n个结点以及每个点初始时对应的权值wi.起始时点与点之间没有连边.有3类操作:  1.bridge A B:询问结点A与结点B是否连通. 如果是则输出“no”.否则输出“yes”,并且在 ...

  6. [BZOJ2843] 极地旅行社(LCT)

    传送门 模板. ——代码 #include <cstdio> #include <iostream> #define N 300001 #define get(x) (son[ ...

  7. 【BZOJ2843】极地旅行社(Link-Cut Tree)

    [BZOJ2843]极地旅行社(Link-Cut Tree) 题面 BZOJ 题解 \(LCT\)模板题呀 没什么好说的了.. #include<iostream> #include< ...

  8. 【BZOJ2843】极地旅行社 离线+树链剖分+树状数组

    [BZOJ2843]极地旅行社 Description 不久之前,Mirko建立了一个旅行社,名叫“极地之梦”.这家旅行社在北极附近购买了N座冰岛,并且提供观光服务.当地最受欢迎的当然是帝企鹅了,这些 ...

  9. [bzoj2843&&bzoj1180]极地旅行社 (lct)

    双倍经验双倍的幸福... 所以另一道是300大洋的世界T_T...虽然题目是一样的,不过2843数据范围小了一点... 都是lct基本操作 #include<cstdio> #includ ...

随机推荐

  1. 3ds Max制作妄想中的外星人形象

    来源:CG游 作者:FedericoScarbini 使用软件:3ds Max, Photoshop, ZBrush 简介 我认为每一个人都曾经在他的人生中的某些时刻妄想着关于外星人的事情;我猜这是很 ...

  2. [SHOI2009]Booking 会场预约

    题目:洛谷P2161. 题目大意:有一些操作,分为两种: A.增加一个从第l天到第r天的预约,并删除与这个预约冲突的其他预约,输出删除了多少个预约. B.输出当前有效预约个数. 两个预约冲突定义为两个 ...

  3. 紫书 习题 11-3 UVa 820 (最大流裸题)

    注意这道题是双向边, 然后直接套模板就ok了. #include<cstdio> #include<algorithm> #include<vector> #inc ...

  4. 通过案例快速学会Picasso图片缓存库

    picasso是Square公司开源的一个Android图形缓存库,官网地址http://square.github.io/picasso/,可以实现图片下载和缓存功能.        下载地址:ht ...

  5. 从头认识Spring-1.16 SpEl对集合的操作(1)-建立集合以及訪问集合的元素,以&lt;util:list/&gt;为例

    这一章节我们来讨论一下怎样建立集合以及訪问集合的元素? 1.建立集合? (1)domain 蛋糕类: package com.raylee.my_new_spring.my_new_spring.ch ...

  6. Effective C++ 条款12

    复制对象时,勿忘其每个成分 作者在本节条款提醒我们,在多重继承的情况下进行copy或者copy assignment 的operator=的编写时,一定要考虑base 类部分数据的初始化后者复制. 对 ...

  7. vncserverpassword改动

    前几天去客户现场,客户说有測试库.Linux下的,帮忙给新建一个数据库,我这么热心的人.是吧 那就開始吧. 一般使用vnc搞图形安装.熟练的打开vnc.输入password,报错!!我愣了几秒,忽然反 ...

  8. Double Vision (Unity 5.0)

    Double Vision (Unity 5.0): 根据 http://http.developer.nvidia.com/CgTutorial/cg_tutorial_chapter03.html ...

  9. zzulioj--1824--BOOM(模拟水)

    1824: BOOM Time Limit: 1 Sec  Memory Limit: 128 MB Submit: 25  Solved: 5 SubmitStatusWeb Board Descr ...

  10. Flume 启动

    Configuration是Flume项目的入口程序了,当我们输入 bin/flume-ng agent --conf conf --conf-file conf/kafka1.properties ...