对 @LHF dalao 的题解进行一些补充说明。因为他讲的实在是太难懂了。最后在 @_•́へ•́╬_ dalao 的帮助下才勉强知道怎么做。不过他的代码非常简洁易懂,有需求的可以去看他的代码。我就不放了。
本文章分析复杂度时认为 与 同阶。
首先需要明确的是, 子树中所有与 的距离模 等于 的节点就是 子树中深度模 等于 (下文设其为 )的节点。这样我们就可以把修改转化为将一个点的子树内所有深度模 为 的节点权值加上 。
显然这种数据结构题不可能一个点一个点地去修改。因此先求出 dfn 序。这样就可以把修改变为对 范围内(下文设其为 )的点进行一次区间操作。
但是我们不可能将 范围内的所有值统一加上某数。因此考虑建立一个以 dfn 序为 轴,深度为 轴的平面直角坐标系。把第 个点放在坐标 上。这样我们就把修改转化为将所有横坐标在 范围内,纵坐标模 的节点权值全部加上 。
考虑直接暴力跳纵坐标,将跳到的水平线的 部分全部加上 。因为 dfn 序与深度不对应的坐标是空着的,没有放点。所以把 的整个部分全部加上 不会影响正确性。
用某种数据结构维护每个纵坐标对应的水平线。当 时,暴跳的复杂度就是 的。查询时直接单点查询,因此复杂度是 的。其中 表示这种数据结构修改的复杂度, 表示它查询的复杂度。因此使用修改 ,查询 的序列分块+差分即可达到最优总复杂度。
当 时,暴跳的时间复杂度可能会直接退化到 。因此考虑根号分治,将这部分特殊处理。开一个 的某种数据结构的数组,记为 。每次修改对 执行一次让 区间加 的操作。询问时给答案加上 即可。修改复杂度为 ,询问复杂度为 。因此使用修改 ,查询 的序列分块即可达到最优总复杂度。
因为这两种处理都用到分块,所以可以直接把散块暴力算,整块再分类讨论。
时空复杂度 。时间限制十分充裕,但空间限制不够。可以通过调块长和根号分治的阈值卡过去。
代码就不放了,有需求的可以去看 @LHF dalao 的题解中的代码。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现