这题说的是给了两棵树,各有100000 个节点,然后Q个操作Q<=50000; 每个操作L1 R1 L2 R2。因为对于每棵树都有一个与本棵树其他点与众不同的值, 最后问 在树上从L1到R1这条路径上与第二棵树L2 到 R2 这条路上的点 的权值相等的有多少个

这题挺麻烦的 写的想吐了

首先将第一棵树进行树剖,然后通过树剖可以离散出这颗树的每个点的编号从1,2,3,4...N1,然后将第二棵树进行树剖,按照树剖的值依次插入,以第一棵树离散出的值为叶节点的函数式线段树,

如果第二棵树的值在第一棵树种中不到,那么就直接将他插在值为0的叶节点上。我们可以知道在书剖中他们在同一条链上是相等的,所以他们在函数式线段树中也是连续的。通过这样我们可以使用类似区间第K大的解法解决这个问题

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <string.h>
#include <vector>
#pragma comment(linker,"/STACk:10240000,10240000")
using namespace std;
const int maxn =;
vector<int> F[][maxn],rea[],fro[];
int p[][maxn],fp[][maxn],XX[],top[][maxn];
int depth[][maxn],num[][maxn],son[][maxn],fa[][maxn];
int L1[maxn],V[maxn],data[][maxn],T[maxn];
int Ls[maxn*],Rs[maxn*],Ve[maxn*],len;
struct point{
int x,loc;
bool operator<(const point &A)const{
return x<A.x||(x==A.x&&loc<A.loc);
}
}PP[maxn];
void inti(int loc, int n){
for(int i=; i<=n; ++i)
F[loc][i].clear();
}
void dfs(int loc, int now, int per,int dep){
fa[loc][now]=per;
son[loc][now]=-;
depth[loc][now]=dep;
num[loc][now]=;
int ge=F[loc][now].size();
for(int i=; i<ge; ++i){
int to = F[loc][now][i];
if(to==per||to==now)continue;
dfs(loc,to,now,dep+);
num[loc][now]+=num[loc][to];
if(son[loc][now]==-||num[loc][ son[loc][now] ]<num[loc][to]) son[loc][now]=to;
}
}
void fine(int loc, int now , int X,int per){
top[loc][now]=X;
XX[loc]++;
p[ loc ][ now ]=XX[ loc ];
fp[ loc ][ XX[loc] ]=now;
if( son[ loc ][ now ] != - )
fine( loc , son[loc][now] , X ,now);
int ge=F[loc][now].size();
for(int i=; i<ge; ++i){
int to=F[loc][now][i];
if( to==son[loc][now]||to==now||to==per ) continue;
fine(loc,to,to,now);
}
}
void inser(int L, int R, int K, int per, int &x){
x = ++len;
Ls[x]=Ls[per];
Rs[x]=Rs[per];
Ve[x]=Ve[per]+;
if(L==R)return ;
int mid=(L+R)>>;
if(K<=mid) inser( L, mid , K, Ls[per] , Ls[x] );
else inser( mid+ , R , K , Rs[per] , Rs[x] );
}
int ansed,Lc,Rc;
void query(int L, int R, int per, int cur){
if(Lc<=L&&R<=Rc){
ansed += Ve[cur]-Ve[per];return;
}
if(L>=R)return ;
int mid = (L+R)>>;
if(Lc<=mid) query(L, mid , Ls[per],Ls[cur]);
if(Rc>mid) query(mid+, R, Rs[per],Rs[cur]);
} void solve(int loc, int p1, int p2){
int f1=top[loc][p1],f2=top[loc][p2];
int num=;
while(f1!=f2){
num++;
if(num>) break;
if(depth[loc][f1]<depth[loc][f2]){
int t=p1; p1=p2; p2=t;
t=f1; f1=f2; f2=t;
}
fro[loc].push_back( p[loc][f1] );
rea[loc].push_back( p[loc][p1] );
p1=fa[loc][f1];
f1=top[loc][p1];
}
if(depth[loc][p1]<depth[loc][p2]){
int t=p1; p1=p2; p2=t;
}
fro[loc].push_back(p[loc][p2]);
rea[loc].push_back(p[loc][p1]);
}
int main()
{
int N1, N2;
while(scanf("%d",&N1)==){
for(int i=; i<N1; ++i){
int f;
scanf("%d",&f);
F[][f].push_back(i+);
}
XX[]=;
dfs(,,,);
fine(,,,);
for(int i=; i<N1; ++i){
scanf("%d",&data[][i]);
PP[i].x = data[][i];
PP[i].loc = i+;
}
sort(PP,PP+N1);
for(int i=; i<N1; ++i)
{
V[i]=PP[i].x;
L1[i]=p[ ][ PP[i].loc ];
} scanf("%d",&N2);
for(int i=; i<N2; ++i){
int fa;
scanf("%d",&fa);
F[][fa].push_back(i+);
}
XX[]=;
dfs(,,,);
fine(,,,);
for(int i=; i<=N2; ++i){
scanf("%d",&data[][i]);
int loc = lower_bound(V,V+N1,data[][i])-V;
if(V[loc]==data[][i]){
data[][i]=L1[loc];
}else data[][i]=;
}
Ls[]=Rs[]=Ve[]=len=;
for(int i=; i <= N2; ++ i ){
int loc=fp[ ][ i ];
inser(,N1,data[ ][ loc ],T[ i- ],T[ i ]);
}
int Q;
scanf("%d",&Q);
for(int i=; i<Q; ++i){
int L1,R1,L2,R2;
scanf("%d%d%d%d",&L1,&R1,&L2,&R2);
rea[].clear(); fro[].clear(); rea[].clear(); fro[].clear();
solve(,L1,R1);
solve(,L2,R2);
ansed=;
for(int j=; j<(int)rea[].size(); ++j){
Lc=fro[][j]; Rc=rea[][j];
if(Lc>Rc){ int t=Lc; Lc=Rc; Rc=t; }
for(int k=; k<(int)rea[].size(); ++k){
int L=fro[][k],R=rea[][k];
if(L>R){ int t=L; L=R; R=t; }
query( ,N1,T[L-],T[R] );
}
}
printf("%d\n",ansed);
}
inti(,N1);
inti(,N2);
}
return ;
}

hdu 5111 树链剖分加函数式线段树的更多相关文章

  1. BZOJ4012[HNOI2015]开店——树链剖分+可持久化线段树/动态点分治+vector

    题目描述 风见幽香有一个好朋友叫八云紫,她们经常一起看星星看月亮从诗词歌赋谈到 人生哲学.最近她们灵机一动,打算在幻想乡开一家小店来做生意赚点钱.这样的 想法当然非常好啦,但是她们也发现她们面临着一个 ...

  2. BZOJ 2243: [SDOI2011]染色 树链剖分 倍增lca 线段树

    2243: [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 256 MB 题目连接 http://www.lydsy.com/JudgeOnline/pr ...

  3. BZOJ 2243:染色(树链剖分+区间合并线段树)

    [SDOI2011]染色Description给定一棵有n个节点的无根树和m个操作,操作有2类:1.将节点a到节点b路径上所有点都染成颜色c:2.询问节点a到节点b路径上的颜色段数量(连续相同颜色被认 ...

  4. HDU 5029 Relief grain 树链剖分打标记 线段树区间最大值

    Relief grain Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://acm.hdu.edu.cn/showproblem.php?pid= ...

  5. HDU 3966 Aragorn's Story(模板题)【树链剖分】+【线段树】

    <题目链接> 题目大意: 给定一颗带点权的树,进行两种操作,一是给定树上一段路径,对其上每个点的点权增加或者减少一个数,二是对某个编号点的点权进行查询. 解题分析: 树链剖分的模板题,还不 ...

  6. 焦作网络赛E-JiuYuanWantstoEat【树链剖分】【线段树】

    You ye Jiu yuan is the daughter of the Great GOD Emancipator. And when she becomes an adult, she wil ...

  7. 【Codeforces】【网络流】【树链剖分】【线段树】ALT (CodeForces - 786E)

    题意 现在有m个人,每一个人都特别喜欢狗.另外还有一棵n个节点的树. 现在每个人都想要从树上的某个节点走到另外一个节点,且满足要么这个人自带一条狗m,要么他经过的所有边h上都有一条狗. 2<=n ...

  8. LOJ2269 [SDOI2017] 切树游戏 【FWT】【动态DP】【树链剖分】【线段树】

    题目分析: 好题.本来是一道好的非套路题,但是不凑巧的是当年有一位国家集训队员正好介绍了这个算法. 首先考虑静态的情况.这个的DP方程非常容易写出来. 接着可以注意到对于异或结果的计数可以看成一个FW ...

  9. HYSBZ 4034 【树链剖分】+【线段树 】

    <题目链接> 题目大意: 有一棵点数为 N 的树,以点 1 为根,且树点有权值.然后有 M 个 操作,分为三种: 操作 1 :把某个节点 x 的点权增加 a . 操作 2 :把某个节点 x ...

随机推荐

  1. laravel 控制器构造方法注入request对象

    IndexController: <?php namespace App\Http\Controllers; use Illuminate\Http\Request; use App\Http\ ...

  2. NUC972学习历程之NUWRITER使用说明以及烧录模式的说明

    3.1 簡介Nu-Writer 工具能幫助使用者透過 USB ISP模式, 將Image檔案放入儲存體中, 例如:SPI Flash設備或 NAND Flash設備.3.2 驅動程式安裝Nu-Writ ...

  3. cocos2dx游戏--欢欢英雄传说--添加游戏背景

    经过一段时间的学习cocos2dx,接下来我想要实践开发一个小游戏,我把它命名为“欢欢英雄传说”,项目名将取为HuanHero.环境:cocos2dx环境:cocos2d-x 3.11.1IDE:Co ...

  4. Jquery checkbox选中问题

    checkbox中有.checked的写法,判断当前是否是选中状态,不过这种是针对[object HTMLInputElement]这种类型的,而对于[object Object]这种类型是不能使用的 ...

  5. poj_3468 线段树

    题目大意 一个数列,每次操作可以是将某区间数字都加上一个相同的整数,也可以是询问一个区间中所有数字的和.(这里区间指的是数列中连续的若干个数)对每次询问给出结果. 思路 对于区间的查找更新操作,可以考 ...

  6. Elasticsearch 常用基本查询

    安装启动很简单,参考官网步骤:https://www.elastic.co/downloads/elasticsearch 为了介绍Elasticsearch中的不同查询类型,我们将对带有下列字段的文 ...

  7. Sun公司的产品AnswerBook存在多种漏洞

    一.未授权管理脚本访问漏洞: 1.受影响版本: Sun-AnswerBook2     1.2-1.4.2 2.攻击测试手段 http://a.b.c.d:8888/ab2/@AdminViewErr ...

  8. CSSOM视图模式(CSSOM View Module)

    一.Window视图属性(window对象) 这些属性可以获取住整个浏览器窗体大小.微软则将这些API称为“Screenview 接口” innerWidth 属性和 innerHeight 属性pa ...

  9. 【BZOJ3280】小R的烦恼 最小费用最大流

    [BZOJ3280]小R的烦恼 Description 小R最近遇上了大麻烦,他的程序设计挂科了.于是他只好找程设老师求情.善良的程设老师答应不挂他,但是要求小R帮助他一起解决一个难题. 问题是这样的 ...

  10. Unity3D 笔记一 初始Unity3D

    一.初步认识Unity 1.Unity支持C#.JavaScript.Boo,JavaScript不是标准语法,常称为UnityScript更合适 2.Update 每一帧都会调用该方法.Start. ...