这一道题咋一看只觉得是离线,可以求出所有的f(1,i,z), 答案就等于f(1,r,z)-f(1,l-1,z)。但是没有具体的做法,但是求LCA的深度和有一个非常巧妙的做法,每加一个点,就把这个点到根的路径上的点权值+1,这样计算某个点和之前所有点LCA深度和就可以统计这个点到根的路径上的点的权值和。这样就可以用树链剖分很快的修改和得出答案,这题就解决了。

    上代码:

#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <algorithm>
#include <queue>
#define N 51000
#define yu 201314
using namespace std; struct sss
{
int place, askp;
int num, nump;
}ask[N*];
struct ss
{
int num, push;
}t[N*];
int n, m, nowplace = ;
int p[N], v[N], next[N], bnum = ;
int ans[N][] = {};
int fa[N], deep[N], siz[N], son[N], w[N], top[N]; bool cmp(sss x, sss y) { return x.place < y.place; } void addbian(int x, int y)
{
bnum++; next[bnum] = p[x]; p[x] = bnum; v[bnum] = y;
} void build_tree(int now, int l, int r)
{
t[now].num = ; t[now].push = ;
if (l == r) return; int mid = (l+r)/;
build_tree(now*, l, mid); build_tree(now*+, mid+, r);
} void dfs_1(int now, int fat, int de)
{
int k = p[now]; fa[now] = fat; deep[now] = de;
int maxsonnum = ; siz[now] = ; son[now] = ;
while (k)
{
if (v[k] != fat)
{
dfs_1(v[k], now, de+);
siz[now] += siz[v[k]];
if (siz[v[k]] > maxsonnum)
{
maxsonnum = siz[v[k]];
son[now] = v[k];
}
}
k = next[k];
}
return;
} void dfs_2(int now, int fat, int nowtop)
{
int k = p[now]; top[now] = nowtop; w[now] = ++nowplace;
if (son[now]) dfs_2(son[now], now, nowtop);
while (k)
{
if (v[k] != son[now] && v[k] != fat)
dfs_2(v[k], now, v[k]);
k = next[k];
}
return;
} void downdate(int now, int l, int r)
{
if (!t[now].push) return; int mid = (l+r)/;
t[now*].push += t[now].push;
t[now*+].push += t[now].push;
t[now*].num += (mid-l+) * t[now].push;
t[now*+].num += (r-mid) * t[now].push;
if (t[now*].num > yu) t[now*].num %= yu;
if (t[now*+].num > yu) t[now*+].num %= yu;
t[now].push = ; return;
} void tadd(int now, int l, int r, int al, int ar)
{
if (al <= l && r <= ar)
{
t[now].num += r-l+;
if (t[now].num > yu) t[now].num %= yu;
t[now].push ++; return;
}
int mid = (l+r)/; downdate(now, l, r);
if (al <= mid) tadd(now*, l, mid, al, ar);
if (ar > mid) tadd(now*+, mid+, r, al, ar);
t[now].num = t[now*].num + t[now*+].num;
if (t[now].num > yu) t[now].num %= yu;
} int task(int now, int l, int r, int al, int ar)
{
if (al <= l && r <= ar) return t[now].num;
int mid = (l+r)/, zans = ; downdate(now, l, r);
if (al <= mid) zans = task(now*, l, mid, al, ar);
if (ar > mid) zans += task(now*+, mid+, r, al, ar);
if (zans > yu) zans %= yu;
return zans;
} int askk(int u, int v)
{
int f1 = top[u], f2 = top[v];
if (deep[f1] < deep[f2]) { swap(f1, f2); swap(u, v); }
if (f1 == f2)
{
if (u == v) return task(, , n, w[u], w[u]);
return task(, , n, min(w[u], w[v]), max(w[u], w[v]));
}
int zans = task(, , n, w[f1], w[u]);
zans += askk(fa[f1], v); if (zans > yu) zans %= yu;
return zans;
} void add(int u, int v)
{
int f1 = top[u], f2 = top[v];
if (deep[f1] < deep[f2]) { swap(f1, f2); swap(u, v); }
if (f1 == f2)
{
if (u == v) tadd(, , n, w[u], w[u]);
else tadd(, , n, min(w[u], w[v]), max(w[u], w[v]));
return;
}
tadd(, , n, w[f1], w[u]); add(fa[f1], v);
} int main()
{
scanf("%d%d", &n, &m); build_tree(, , n);
for (int i = ; i < n; ++i)
{
int x; scanf("%d", &x);
addbian(x+, i+);
}
dfs_1(, , ); dfs_2(, , );
for (int i = ; i <= m; ++i)
{
int x, y, z; scanf("%d%d%d", &x, &y, &z); x++; y++; z++;
ask[i*-].place = x-; ask[i*-].askp = z;
ask[i*-].num = i; ask[i*-].nump = ;
ask[i*].place = y; ask[i*].askp = z;
ask[i*].num = i; ask[i*].nump = ;
}
sort(ask+, ask++*m, cmp); int nowplace = ;
for (int i = ; i <= m*; ++i)
{
while (ask[i].place > nowplace)
{
nowplace++;
add(, nowplace);
}
if (ask[i].place)
ans[ask[i].num][ask[i].nump] = askk(, ask[i].askp);
else ans[ask[i].num][ask[i].nump] = ;
}
for (int i = ; i <= m; ++i)
printf("%d\n", (ans[i][]+yu-ans[i][]) % yu);
return ;
}

bzoj 3626 LCA的更多相关文章

  1. BZOJ 3626 LCA(离线+树链剖分)

    首先注意到这样一个事实. 树上两个点(u,v)的LCA的深度,可以转化为先将u到根路径点权都加1,然后求v到根路径上的总点权值. 并且该题支持离线.那么我们可以把一个区间询问拆成两个前缀和形式的询问. ...

  2. BZOJ 3626 LCA(离线+树链剖分+差分)

    显然,暴力求解的复杂度是无法承受的. 考虑这样的一种暴力,我们把 z 到根上的点全部打标记,对于 l 到 r 之间的点,向上搜索到第一个有标记的点求出它的深度统计答案.观察到,深度其实就是上面有几个已 ...

  3. [BZOJ 3626] [LNOI2014] LCA 【树链剖分 + 离线 + 差分询问】

    题目链接: BZOJ - 3626 题目分析 考虑这样的等价问题,如果我们把一个点 x 到 Root 的路径上每个点的权值赋为 1 ,其余点的权值为 0,那么从 LCA(x, y) 的 Depth 就 ...

  4. BZOJ 3626: [LNOI2014]LCA [树链剖分 离线|主席树]

    3626: [LNOI2014]LCA Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 2050  Solved: 817[Submit][Status ...

  5. bzoj 3626 [LNOI2014]LCA(离线处理+树链剖分,线段树)

    3626: [LNOI2014]LCA Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1272  Solved: 451[Submit][Status ...

  6. bzoj 3626: [LNOI2014]LCA 离线+树链剖分

    3626: [LNOI2014]LCA Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 426  Solved: 124[Submit][Status] ...

  7. BZOJ 3626: [LNOI2014]LCA( 树链剖分 + 离线 )

    说多了都是泪啊...调了这么久.. 离线可以搞 , 树链剖分就OK了... -------------------------------------------------------------- ...

  8. BZOJ 3626 [LNOI2014]LCA:树剖 + 差分 + 离线【将深度转化成点权之和】

    题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=3626 题意: 给出一个n个节点的有根树(编号为0到n-1,根节点为0,n <= 50 ...

  9. BZOJ 3626 [LNOI2014]LCA 树剖+(离线+线段树 // 在线+主席树)

    BZOJ 4012 [HNOI2015]开店 的弱化版,离线了,而且没有边权(长度). 两种做法 1 树剖+离线+线段树 这道题求的是一个点zzz与[l,r][l,r][l,r]内所有点的lcalca ...

随机推荐

  1. android 用ListView实现表格样式

    原文:http://blog.csdn.net/centralperk/article/details/8016350 效果图: 源码下载地址:http://download.csdn.net/det ...

  2. Android 使用 Gmail 来发送邮件

    Android 使用 Gmail 来发送邮件 1. [代码]SendMail.java package org.apache.android.mail; import android.app.Acti ...

  3. js判断图片是否显示

    function getDefaultImg() { //添加判断图片是否存在操作 var $defaultImgPathObj = $('input[name=defaultImgPath]'); ...

  4. 简简单单安装debian桌面工作环境

    linux一般给人的影响是对使用者的要求偏高, 使用者需要自行配置很多相应的系统工作参数,因此,从一定的程度上阻碍了用户去使用它.而本文所介绍的是, 使用者完全可以消除这个障碍,非常简单地安装好自己的 ...

  5. 项目源码--Android本地音乐播放器

    下载源码 技术要点: 1.本地音乐播放与管理 2.支持在线下载 3.非库音频流的解码 4. UI控件的综合使用 5. HTTP通信模块 6. Mysql数据库的综合使用 7. 后台服务技术 8. 源码 ...

  6. Android 高级UI设计笔记08:Android开发者常用的7款Android UI组件(转载)

    Android开发是目前最热门的移动开发技术之一,随着开发者的不断努力和Android社区的进步,Android开发技术已经日趋成熟,当然,在Android开源社区中也涌现了很多不错的开源UI项目,它 ...

  7. 错误与修复:ASP.NET无法检测IE10,导致_doPostBack未定义JavaScript错误,恒处于FF5卷动条位置

    浏览器版本号继续升级过程中.IE9诞生了,IE10 也即将问世,火狐5和6已经发布了,而7和8也快出现了,Opera已经到了11,Chrome还在继续,我也不知道,应该总在14和50之间吧.不管怎样, ...

  8. 安装tomcat 证书

    创建证书keystore 1)      Mdmc用户登录服务器,执行如下命令: keytool -genkey -v -alias tomcat -keyalg RSA -keystore tomc ...

  9. Xquartz远程访问linux

    实验环境:mac 操作系统:         OS X 10.9.4 Mavericksmac IP                      192.168.1.106XQuartz:       ...

  10. ServiceStack.Redis客户端访问库几项事项

    1)RedisClient的SetValue(string key, byte[]val)方法,如果val的长度为0,则redis服务器库中设置该key值失败. 2)PoolRedisClientMa ...