动态树分治,用三个set分别维护每个重心到每一个子树的距离种类、每个重心所有子树的最大值和次大值、全局答案的最大值。复杂度O(nlogn^2)

  代码

 #include<cstdio>
#include<algorithm>
#include<vector>
#include<set>
#define pb push_back
using namespace std;
const int N = ;
int size[N],flag[N],n,a,b,i,f[N],cnt,typ[N],deep[N];
int jump[N][];
int q;
char ch[];
vector<int> e[N];
multiset<int> dist[N],ans[N],Ans;
multiset<int>::iterator it;
int getroot(int x,int fa,int n)
{
int i,tmp=,rt=;
size[x]=;
for (i=;i<e[x].size();i++)
if ((e[x][i]!=fa)&&(!flag[e[x][i]]))
{
rt|=getroot(e[x][i],x,n);
size[x]+=size[e[x][i]];
if (size[e[x][i]]>n/) tmp=;
}
if (n-size[x]>n/) tmp=;
if (tmp==) return rt;else return x;
}
void gao(int x,int fa,int y,int dis)
{
dis++;
int i;
dist[y].insert(dis);
for (i=;i<e[x].size();i++)
if ((!flag[e[x][i]])&&(e[x][i]!=fa))
gao(e[x][i],x,y,dis);
}
void DFS(int x,int fa)
{
int i;
deep[x]=deep[fa]+;
jump[x][]=fa;
for (i=;i<=;i++)
jump[x][i]=jump[jump[x][i-]][i-];
for (i=;i<e[x].size();i++)
if (e[x][i]!=fa) DFS(e[x][i],x);
}
int lca(int a,int b)
{
int i;
if (deep[a]<deep[b]) a^=b^=a^=b;
for (i=;i>=;i--)
if (deep[jump[a][i]]>=deep[b]) a=jump[a][i];
if (a==b) return a;
for (i=;i>=;i--)
if (jump[a][i]!=jump[b][i]) a=jump[a][i],b=jump[b][i];
return jump[a][];
}
int getdis(int x,int y)
{
int z=lca(x,y);
return deep[x]+deep[y]-*deep[z];
}
void del(int x)
{
int tmp=;
if (ans[x].size()>=)
{
it=ans[x].end();
--it;tmp+=*it;
--it;tmp+=*it;
it=Ans.lower_bound(tmp);
Ans.erase(it);
}
}
void ins(int x)
{
int tmp=;
if (ans[x].size()>=)
{
it=ans[x].end();
--it;tmp+=*it;
--it;tmp+=*it;
Ans.insert(tmp);
}
}
void DEL(int y)
{
if (dist[y].size())
{
it=dist[y].end();--it;
int tmp=*it;
it=ans[f[y]].lower_bound(tmp);
ans[f[y]].erase(it);
}
}
void INS(int y)
{
if (dist[y].size())
{
it=dist[y].end();--it;
int tmp=*it;
ans[f[y]].insert(tmp);
}
}
int change(int x,int y)
{
del(x);
if (typ[x]==)
{
it=ans[x].lower_bound();
ans[x].erase(it);
}
else
ans[x].insert();
while (x)
{
ins(x);
if (f[x])
{
del(f[x]);
DEL(x);
int dis=getdis(f[x],y);
if (typ[y]==)
{
it=dist[x].lower_bound(dis);
dist[x].erase(it);
}
else
dist[x].insert(dis);
INS(x);
}
x=f[x];
}
}
int dfs(int x,int n,int fa)
{
int i,y;
x=getroot(x,,n);
f[x]=fa;
flag[x]=;
ans[x].insert();
for (i=;i<e[x].size();i++)
if (!flag[e[x][i]])
{
if (size[e[x][i]]>size[x])
y=dfs(e[x][i],n-size[x],x);
else
y=dfs(e[x][i],size[e[x][i]],x);
gao(e[x][i],,y,);
it=dist[y].end();
ans[x].insert(*(--it));
}
ins(x);
flag[x]=;
return x;
}
int main()
{
scanf("%d",&n);
for (i=;i<n;i++)
{
scanf("%d%d",&a,&b);
e[a].pb(b);
e[b].pb(a);
}
dfs(,n,);
DFS(,);
scanf("%d",&q);
for (i=;i<=q;i++)
{
scanf("%s",ch+);
if (ch[]=='G')
{
if (cnt==n)
printf("-1\n");
else
if (cnt==n-)
printf("0\n");
else
{
it=Ans.end();--it;
printf("%d\n",*it);
}
}
else
if (ch[]=='C')
{
scanf("%d",&a);
if (typ[a]==)
cnt++,typ[a]=;
else
cnt--,typ[a]=;
change(a,a);
}
}
}

BZOJ1095 [ZJOI2007]Hide 捉迷藏的更多相关文章

  1. 动态点分治:Bzoj1095: [ZJOI2007]Hide 捉迷藏

    简介 这是我自己的一点理解,可能写的不好 点分治都学过吧.. 点分治每次找重心把树重新按重心的深度重建成了一棵新的树,称为分治树 这个树最多有log层... 动态点分治:记录下每个重心的上一层重心,这 ...

  2. [bzoj1095][ZJOI2007]Hide 捉迷藏 点分树,动态点分治

    [bzoj1095][ZJOI2007]Hide 捉迷藏 2015年4月20日7,8876 Description 捉迷藏 Jiajia和Wind是一对恩爱的夫妻,并且他们有很多孩子.某天,Jiaji ...

  3. BZOJ1095:[ZJOI2007]Hide 捉迷藏(动态点分治)

    Description 捉迷藏 Jiajia和Wind是一对恩爱的夫妻,并且他们有很多孩子.某天,Jiajia.Wind和孩子们决定在家里玩 捉迷藏游戏.他们的家很大且构造很奇特,由N个屋子和N-1条 ...

  4. BZOJ1095: [ZJOI2007]Hide 捉迷藏【线段树维护括号序列】【思维好题】

    Description 捉迷藏 Jiajia和Wind是一对恩爱的夫妻,并且他们有很多孩子.某天,Jiajia.Wind和孩子们决定在家里玩 捉迷藏游戏.他们的家很大且构造很奇特,由N个屋子和N-1条 ...

  5. BZOJ1095: [ZJOI2007]Hide 捉迷藏【动态点分治】

    Description 捉迷藏 Jiajia和Wind是一对恩爱的夫妻,并且他们有很多孩子.某天,Jiajia.Wind和孩子们决定在家里玩 捉迷藏游戏.他们的家很大且构造很奇特,由N个屋子和N-1条 ...

  6. bzoj千题计划245:bzoj1095: [ZJOI2007]Hide 捉迷藏

    http://www.lydsy.com/JudgeOnline/problem.php?id=1095 查询最远点对,带修改 显然可以用动态点分治 对于每个点,维护两个堆 堆q1[x] 维护 点分树 ...

  7. BZOJ1095 [ZJOI2007]Hide 捉迷藏 动态点分治 堆

    原文链接https://www.cnblogs.com/zhouzhendong/p/BZOJ1095.html 题目传送门 - BZOJ1095 题意 有 N 个点,每一个点是黑色或者白色,一开始所 ...

  8. BZOJ1095 [ZJOI2007]Hide 捉迷藏 【动态点分治 + 堆】

    题目链接 BZOJ1095 题解 传说中的动态点分治,一直不敢碰 今日一会,感觉其实并不艰涩难懂 考虑没有修改,如果不用树形dp的话,就得点分治 对于每个重心,我们会考虑其分治的子树内所有点到它的距离 ...

  9. bzoj1095: [ZJOI2007]Hide 捉迷藏 线段树维护括号序列 点分治 链分治

    这题真是十分难写啊 不管是点分治还是括号序列都有一堆细节.. 点分治:时空复杂度$O(n\log^2n)$,常数巨大 主要就是3个堆的初始状态 C堆:每个节点一个,为子树中的点到它父亲的距离的堆. B ...

随机推荐

  1. JS: How to detect my browser version and operating system using JavaScript?

    Example: 1. for IE 11,  navigator.userAgent  returns "Mozilla/5.0 (Windows NT 6.1; WOW64; Tride ...

  2. Python for Infomatics 第12章 网络编程一(译)

    注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 本书中的许多例子关注的是读取文件 ...

  3. HDU 3306 Another kind of Fibonacci(快速幂矩阵)

    题目链接 构造矩阵 看的题解,剩下的就是模板了,好久没写过了,注意取余. #include <cstring> #include <cstdio> #include <s ...

  4. js获取?后面具体参数的值

    function getURLParam(name) {         return decodeURIComponent((new RegExp('[?|&]' + name + '=' ...

  5. IOS_ios逆向工程-静态分析

    返回博客列表 原 ios逆向工程-静态分析 余成海 发布时间: 2014/11/03 19:17 阅读: 11201 收藏: 17 点赞: 5 评论: 6 最近在学习IOS逆向工程,查看网络上的资料也 ...

  6. CSS常用属性

    //边界线 border: 1px solid #E4E4E4; //绝对 定位 position: absolute; //相对定位 position: relative; //超出部分隐藏 ove ...

  7. MySQL支持的数据类型(2)( 日期)

    日期和时间类型 字节 最小值 最大值 date 4 1000-01-01 9999-12-31 datetime 8 1000-01-01 00:00:00 9999-12-31 23:59:59 t ...

  8. Html简单介绍

    一.Html 1.万维网的核心语言,高大上称之为超文本标记语言(Html)的第五次修改 2.完成的时间:2014年10月29日 3.我们需要了解有一定高度的知识: WHATWG  WEB超文本应用技术 ...

  9. USACO 2014 FEB 银组

    1.自动打字{Silver题1} [问题描述] 贝西新买了手机,打字不方便,请设计一款应用,帮助她快速发消息. 字典里有W(W<=30000)个小写字母构成的单词,所有单词的字符总数量不超过1, ...

  10. canvas中的rotate的使用方法

    今天在绘制一个足球滚动的时候,想使用rotate方法,之前看到这个方法的时候,并没有引起任何重视,无非就是和CSS3里的rotate一样的用么... 遗憾的是,事实并非如此,由于代码在公司,我也就不去 ...