当前位置: 首页 > news >正文

*题解:P5384 [Cnoi2019] 雪松果树

原题链接

解析

首先,求完 \(k\) 级祖先后,问题转化为求一个结点子树内指定深度的结点个数。一个很朴素的想法是,每个结点上维护一个数组 \(cnt\)\(cnt_i\) 表示子树内深度为 \(i\) 的结点个数,把子树信息简单合并一下就可以得到答案。为了优化合并效率与空间,可以使用动态开点线段树来进行线段树合并。

时间复杂度 \(O(n\log n)\),空间复杂度 \(O(n\log n)\)

然而,256MiB 的空间限制并不允许额外贡献三个 \(O(n\log n)\) 大小数组的线段树合并通过。

让我们来看一个在线做法。先求 DFS 序,将树拍平成序列。我们知道子树内结点在 DFS 序中对应着一段连续的区间:\([dfn_x,dfn_x + siz_x - 1]\),其中 \(dfn_x\) 表示点 \(x\) 的 DFS 序,\(siz_x\) 表示以 \(x\) 为根子树大小。所以原问题相当于求区间内指定数的个数,可以离线后用树状数组解决,在这里不多赘述。对于在线做法,考虑将所有结点按照深度分类,并按照 DFS 序排序,这样查询时只需在对应数列 \(a\) 中二分左右端点 \(l,r\) 使得 \(l\) 是满足 \(a_l>dfn_x\) 的最小 \(l\)\(r\) 是满足 \(a_r \le dfn_x + siz_x - 1\) 的最大 \(r\)

时间复杂度 \(O(m\log n)\),空间复杂度 \(O(n\log n)\)(如果用了倍增求 \(k\) 级祖先)。

代码

注意题目要求统计时不包含 \(u\)

#include <bits/stdc++.h>
#define ls(x) ((x) << 1)
#define rs(x) ((x) << 1 | 1)
#define mid (l + r >> 1)
using namespace std;
const int N = 1e6 + 5,M = 20;
typedef long long ll;
typedef pair<int,int> pii;
int dep[N],fa[N][M],siz[N],dfn[N];
vector<int> t[N],p[N];
int cnt;
void dfs(int x){dfn[x] = ++cnt;dep[x] = dep[fa[x][0]] + 1;siz[x] = 1;p[dep[x]].push_back(dfn[x]);for(int i=1;i<M;i++){fa[x][i] = fa[fa[x][i - 1]][i - 1];}for(int nx : t[x])if(nx != fa[x][0]){dfs(nx);siz[x] += siz[nx];}
}
int get(int a,int b){for(int i=M - 1;i>=0;i--){if(b & (1 << i)){a = fa[a][i];}}return a;
}
int sol(int x,int k){if(!x) return 0;int a = lower_bound(p[k].begin(),p[k].end(),dfn[x]) - p[k].begin();int b = upper_bound(p[k].begin(),p[k].end(),dfn[x] + siz[x] - 1) - p[k].begin();return b - a - 1;
}
int main(){ios::sync_with_stdio(false);cin.tie(0);
//	freopen("in.txt","r",stdin);
//	freopen("out.txt","w",stdout);int n,q;cin>>n>>q;for(int i=2;i<=n;i++){cin>>fa[i][0];	t[fa[i][0]].push_back(i);t[i].push_back(fa[i][0]);}dfs(1);for(int i=1;i<=q;i++){int u,k;cin>>u>>k;cout<<sol(get(u,k),dep[u])<<" ";}return 0;
}
http://www.jsqmd.com/news/715154/

相关文章:

  • TEK Launcher:ARK生存进化玩家的终极启动器解决方案
  • OpCore Simplify实战指南:高效自动化OpenCore EFI配置的最佳实践
  • 内存化系统是怎么设计的?
  • 别再搞混了!一张图看懂YOLOv5各版本核心模块演变(Focus/C3/SPPF对比)
  • 手把手教你写出优雅高效的SQL:从入门到精通
  • SpringBoot项目里,Mybatis-Plus的主键策略(IdType)到底怎么选?AUTO、INPUT还是NONE?
  • Hacklock未来展望:AI时代下图案锁安全测试的发展趋势
  • rope集成VSCode与PyCharm:在IDE中实现智能重构
  • 2026中国钛合金棒厂家TOP4权威排名:医用钛棒/TC4钛棒首选供应商 - 深度智识库
  • (Linux)进程控制
  • LeetCode 深度优先搜索(DFS)题解
  • 猫抓浏览器扩展完全指南:免费开源资源嗅探工具终极教程
  • 从感受野计算到代码实现:用Python可视化带你彻底搞懂空洞卷积的等效卷积核
  • 3个关键步骤:实现浏览器媒体资源智能捕获的完整方案
  • axilite + ap_memory约束数组-突破单口RAM限制
  • AI赋能的个性化国际教育崛起:2026深圳国际学校革命性择校指南 - 深度智识库
  • 三步掌握SakuraFrp:内网穿透终极实战指南
  • Kodi IPTV Simple完整指南:3步搭建专业级家庭电视直播系统
  • 瑞芯微(EASY EAI)RV1126B ROS2安装
  • 你的宽带真的支持IPv6吗?手把手教你用手机热点+MobaXterm远程办公
  • 避坑指南:在Ruoyi-Vue中实现登录拦截与密码重置,我踩了这三个Token管理的坑
  • 2026年数控钣金公司实力排行/钣金,钣金加工,钣金件加工,精密不锈钢钣金加工 - 品牌策略师
  • Amulet-Map-Editor完整功能解析:从世界编辑到格式转换
  • Yew物联网:MQTT和WebSocket通信的终极指南
  • 终极Python多线程与多进程编程指南:从入门到实践的完整路径
  • 如何利用Composer二进制包支持高效分发PHP扩展和工具
  • Smithbox终极指南:如何轻松修改你最喜欢的魂系游戏
  • 一键安装HS2-HF_Patch:解锁Honey Select 2完整游戏体验的终极指南
  • OpCore Simplify:3步完成黑苹果OpenCore配置的完整指南
  • 2026年,还想要入局大模型领域的学习和工作,还来得及吗?红利期还在吗?