SPOJcot2 Count on a tree II (树上莫队)
You are given a tree with N nodes. The tree nodes are numbered from 1 to N. Each node has an integer weight.
We will ask you to perform the following operation:
- u v : ask for how many different integers that represent the weight of nodes there are on the path from u to v.
Input
In the first line there are two integers N and M. (N <= 40000, M <= 100000)
In the second line there are N integers. The i-th integer denotes the weight of the i-th node.
In the next N-1 lines, each line contains two integers u v, which describes an edge (u, v).
In the next M lines, each line contains two integers u v, which means an operation asking for how many different integers that represent the weight of nodes there are on the path from u to v.
Output
For each operation, print its result.
Example
Input:
8 2
105 2 9 3 8 5 7 7
1 2
1 3
1 4
3 5
3 6
3 7
4 8
2 5
7 8
Output:
4
4
题意:求两点间点权值的种类数量。
之前讲过了如何“皇室联邦分块”,由于此题没有要求在线,就先分块,然后莫队就行了。
每次转移的时候怕出错,就干脆vis标记即可。
此题还有很多在线的做法。强得不行。。。ORZ
#include<cmath>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
const int maxn=;
const int maxm=;
int n,m,group[maxn]; struct in
{
int x; int y; int id;
friend bool operator< (in a,in b)
{
return group[a.x]!=group[b.x]?group[a.x]<group[b.x]:group[a.y]<group[b.y];
}
}q[maxm]; struct Solve
{
int maxi;
int Next[maxn<<],Laxt[maxn],To[maxn<<],cnt,delta;
int num[maxn],dep[maxn],anc[maxn][],w[maxn],wx[maxn];
int B,stc[maxn],top,tot,ans[maxm],vis[maxn]; int swap(int &u,int &v) { u^=v;v^=u;u^=v;}
int read()
{
int res=;bool t=false; char c=getchar();
while(c>''||c<'') { if(c=='-') t=true; c=getchar();}
while(c<=''&&c>='') { res=(res<<)+(res<<)+c-'';c=getchar();}
if(t) return -res; return res;
} void add(int u,int v)
{
Next[++cnt]=Laxt[u];
Laxt[u]=cnt; To[cnt]=v;
} void init()
{
int u,v; B=sqrt(n);
for(int i=;(<<i)<=n;i++) maxi=i;
for(int i=;i<=n;i++) scanf("%d",&w[i]);
for(int i=;i<=n;i++) wx[i]=w[i];
sort(wx+,wx+n+);
int tt=unique(wx+,wx+n+)-(wx+);
for(int i=;i<=n;i++)
w[i]=lower_bound(wx+,wx+tt+,w[i])-wx;
for(int i=;i<n;i++){
scanf("%d%d",&u,&v);
add(u,v); add(v,u);
}
dep[]=; dfs();
while(top) group[stc[top--]]=tot;//最后剩余部分莫忘liao。
for(int i=;i<=m;i++) {
q[i].id=i, scanf("%d%d",&q[i].x,&q[i].y);
if(group[q[i].x]<group[q[i].y]) swap(q[i].x,q[i].y);//稍微调整一下,可能会优化。
}
sort(q+,q+m+); get_LCA();
} void dfs(int u)
{
int Now=top;
for(int i=Laxt[u];i;i=Next[i])
if(!dep[To[i]]){
anc[To[i]][]=u; dep[To[i]]=dep[u]+; dfs(To[i]);
if(top-Now>=B) {
++tot; while(top!=Now) group[stc[top--]]=tot;
}
}
stc[++top]=u;
} void get_LCA()
{
for(int i=;i<=maxi;i++)
for(int j=;j<=n;j++)
anc[j][i]=anc[anc[j][i-]][i-];
} int LCA(int u,int v)
{
if(dep[u]<dep[v]) swap(u,v);
for(int i=maxi;i>=;i--)
if(dep[anc[u][i]]>=dep[v]) u=anc[u][i];
if(u==v) return u;
for(int i=maxi;i>=;i--){
if(anc[u][i]!=anc[v][i]){
u=anc[u][i];
v=anc[v][i];
}
} return anc[u][];
} void trans(int &u)
{
if(vis[u]) //已被记录,则本次去掉此点
{
if(--num[w[u]] == ) delta--;
}
else if(++num[w[u]] == ) delta++;
vis[u] ^= ;
u=anc[u][];
} void solve()
{
int su=,sv=; delta=;
for(int i = ; i <= m; i++)
{
int tu=q[i].x,tv=q[i].y;
int lca=LCA(su, tu);//两点朝lca移动,处理路径上的点
while(su!=lca) trans(su);
while(tu!=lca) trans(tu);
lca=LCA(sv,tv);
while(sv!=lca) trans(sv);
while(tv!=lca) trans(tv);
su=q[i].x,sv=q[i].y;
lca=LCA(sv, su);
ans[q[i].id]=delta+(!num[w[lca]]);//对lca特殊处理
}
for(int i=;i<=m;i++) printf("%d\n",ans[i]);
}
}Tree;
int main()
{
scanf("%d%d",&n,&m);
Tree.init();
Tree.solve();
return ;
}
SPOJcot2 Count on a tree II (树上莫队)的更多相关文章
- spoj COT2 - Count on a tree II 树上莫队
题目链接 http://codeforces.com/blog/entry/43230树上莫队从这里学的, 受益匪浅.. #include <iostream> #include < ...
- SP10707 COT2 - Count on a tree II (树上莫队)
大概学了下树上莫队, 其实就是在欧拉序上跑莫队, 特判lca即可. #include <iostream> #include <algorithm> #include < ...
- [SPOJ]Count on a tree II(树上莫队)
树上莫队模板题. 使用欧拉序将树上路径转化为普通区间. 之后莫队维护即可.不要忘记特判LCA #include<iostream> #include<cstdio> #incl ...
- SP10707 COT2 - Count on a tree II [树上莫队学习笔记]
树上莫队就是把莫队搬到树上-利用欧拉序乱搞.. 子树自然是普通莫队轻松解决了 链上的话 只能用树上莫队了吧.. 考虑多种情况 [X=LCA(X,Y)] [Y=LCA(X,Y)] else void d ...
- SPOJ COT2 Count on a tree II 树上莫队算法
题意: 给出一棵\(n(n \leq 4 \times 10^4)\)个节点的树,每个节点上有个权值,和\(m(m \leq 10^5)\)个询问. 每次询问路径\(u \to v\)上有多少个权值不 ...
- SPOJCOT2 Count on a tree II
分析 树上莫队裸题. 好博客 树剖的时候不能再次dfs重儿子.(好像是废话,但我因为这个问题调了三小时) 代码 #include<cstdlib> #include<cstdio&g ...
- P4074 [WC2013]糖果公园 树上莫队带修改
题目链接 Candyland 有一座糖果公园,公园里不仅有美丽的风景.好玩的游乐项目,还有许多免费糖果的发放点,这引来了许多贪吃的小朋友来糖果公园游玩. 糖果公园的结构十分奇特,它由 nn 个游览点构 ...
- 【SPOJ】Count On A Tree II(树上莫队)
[SPOJ]Count On A Tree II(树上莫队) 题面 洛谷 Vjudge 洛谷上有翻译啦 题解 如果不在树上就是一个很裸很裸的莫队 现在在树上,就是一个很裸很裸的树上莫队啦. #incl ...
- SPOJ COT2 - Count on a tree II(LCA+离散化+树上莫队)
COT2 - Count on a tree II #tree You are given a tree with N nodes. The tree nodes are numbered from ...
随机推荐
- 【转载】面向切面编程(AOP)学习
看到这篇文章,学习一下:http://www.ciaoshen.com/2016/10/28/aop/ 想理清一下从“动态代理”,到 “注释”,到“面向切面编程”这么一个技术演进的脉络. 只想讲清楚两 ...
- react 调用 function 的写法 及 解决 react onClick 方法自动执行
1.react 调用方法的写法 (1)方式一 onClick={this.getFetchData.bind(this,item.id)} (2)方式二 getFetchData(e){ this.s ...
- 菜鸟调错(十)——启动Tomcat报错“Unsupported major.minor version xxx ”
近期项目更新JDK,由之前的1.7更新到1.8. 下载并安装好新的JDK以后,编译.启动Tomcat的时候,报错了.提示:"Unsupported major.minor version x ...
- iOS 摇一摇的实现
- (void)viewDidLoad { [super viewDidLoad]; [[UIApplication sharedApplication] setApplicationSupports ...
- caffe2--ubuntu16.04--14.04--install
Install Welcome to Caffe2! Get started with deep learning today by following the step by step guide ...
- 错误 1 error C1083: 无法打开包括文件: “numpy/arrayobject.h”: No such file
问题:错误 1 error C1083: 无法打开包括文件: “numpy/arrayobject.h”: No such file 解答:加入include路径:E:\env\Anaconda2x6 ...
- 集群服务器状态命令------rs.status()各个字段的含义
可根据rs.status() 查询集群服务器状态.字段解释: self 这个信息出现在执行rs.status()函数的成员信息中 stateStr用户描述服务器状态的字符串.有SECONDARY,PR ...
- Hadoop集群_HDFS初探之旅
1.HDFS简介 HDFS(Hadoop Distributed File System)是Hadoop项目的核心子项目,是分布式计算中数据存储管理的基础,是基于流数据模式访问和处理超大文件的需求而开 ...
- js中变量的声明
大家都知道js中变量的声明是要提前的,下面有4个样例: 1.if(!"t" in window){ var t = 1; } alert(t);答案是undefine ...
- registerForRemoteNotificationTypes: is not supported in iOS 8.0 and later
本文转载至 http://bbs.csdn.net/topics/390889517 IOS8 PUSH解决方法 昨天晚上整理PUSH的东西,准备些一个教程,全部弄好之后,发现没有达到预期的效果,本以 ...