> 查询 Ynoi 含量中......
根号含量为 0,精神状态良好!
CF1793F / CF765F / P5926 D
区间一维最近点对。.
首先一个问题就是把有用的点对找出来,使得答案一定出现在这些点对当中。在值域上按照中位数划分做一个分治,看 之间的贡献,记 ,然后贡献就是 ,如果 出现在同一边也没有关系因为求的是 .然后按照原数组的下标排序,考虑一对有用的 ,必须满足 的 都不会比其更优,那就是 ,即 .
这样话,维护一个递增的单调栈,每次压入一个 ,与其组成关键点对 的 一定是被 弹出的,以及最后一个未被弹出的那个。这样这么一次划分关键点对个数就是 个,总的个数就是 个。时间复杂度也是 .
另一个思考方向是:考虑 , 那么 无用.也就是 则 无用,那么对于 寻找支配点,就直接查一下 的 中, 的前驱和后继是啥就行(想一想,为什么这里没考虑 的 )。实际上和上面那个找出来的是一样的。
然后就是 复杂度的 2-side ,这里 是点的个数其为 .
首先对 作扫描线,维护后缀 的单调栈。假如这样插入红点,查询一下红点的下标的前驱,看上面的值是不是大于红点的权值,如果大于就删掉。所以对下标开一棵 vEB 就可以了,然后查询就是查一下 在单调栈里的后继上挂的值。
卡空间 01 Trie B
一条边上可以有好多个数,也就是把只有一个儿子的节点给合并到一起。这样每次插入的时候最多只会新建两个节点了。需要位运算实现 查询二进制数的 lcp.
P7476 D
没有 2 操作怎么做/fn 线段树套堆,插入的时候在只插线段树划分出的区间里。查询的时候就是定位到的都查一下(标记永久化)。然后还要维护子树堆顶 max.
删除操作的话就直接把走到的节点需要删的就删掉然后结束递归。当询问区间并非完全包含当前节点代表区间时,还需要把误删的加回来。然后发现“把误删的加回来”最多只有两次,也就是左右两端的时候。所以每次只会增加 个段。
现在加入和删除的段数是 的了,然后考虑向下递归的时候必然是要加入一个段或者删除一个段,所以向下递归的复杂度也是 ,那么总复杂度就是 .
P4786 D
,使得前缀和都 ,后缀和都 .暴力怎么做?前搞出前缀和,然后把如果前缀 更新为负数了就贪心改掉,然后再倒过来改。需要把这个过程写成式子的形式:先花费 ,然后考虑 后缀删的个数就 即 ,然后再花费 .
那么总的花费就是:
.
线段树维护分治信息。
LOJ6507 B
猜到是某种势能均摊了,但是没想明白这个均摊为啥对的。
上棵线段树,记录这个区间有哪些位是已经被 区间或/与 确定好具体值的,那么再对这个区间整体覆盖这一位的时候就能得知答案了,否则继续往下递归。
考虑将每个节点的势能设置为不完全一致的位数。势能每次最多只会增加 ,然后花费的时间复杂度就是释放了多少势能。
P5069 D
这个题目名很美。
拉了,没看出来。注意到如果操作一个位置,那么它两边的位置就一定不会被操作了,所以就可以将答案加上这个数然后删掉它和它旁边的数。那么考虑每一个峰,答案就是这些峰的值以及中间的奇数和或者偶数和。树状数组维护一下,每次单点修改的时候讨论一下搞出答案的变化量就行。
这位更是重量级的做法是线段树维护分治信息。依然是考虑一个点选了之后它两边就一定不会被选所以可以删掉。然后考虑线段树去合并分治信息,那么就需要记录一下 表示有没有带左端点,有没有带右端点,的答案是什么。还要记 表示这种情况下左/右端点有没有选。
这个的好处是可以支持区间查询,区间加。
P5070 D
按 作扫描线,加入一个 的时候把 里所有值最后一次出现的位置给提出来,从右往左扫,处理出答案的变化,那么就变成区间加单点查。
P5576 D
先考虑 个串的最长公共子串有啥做法,然后进行一下魔改。
首先就是把它们都查到广义 SAM 里面,然后看子树中有所有串 endpos 的节点的 len 的最大值。
现在是区间询问,那么就是包含颜色 的节点的 len 的最大值。在 parent 树上线段树合并好像不太行,那就 set 维护连续颜色段然后启发式合并。保证 从大到小合并,每次合并出一个 之后,考虑它成为那些点的答案,对于每个询问 将 挂到 上,通过线段树记录区间最小值就能找出能更新的询问,更新完之后再在线段树里把这个询问删掉。这样复杂度就是 polylog 的。
ICPC 2022 Jinan L B
https://codeforces.com/gym/104076/problem/L
看上去很经典,想一想发现不是很会。那就考虑一下特殊情况,发现链的情况就是区间一维最近点对(CF1793F / CF765F / P5926),那还是得从那个题搬做法来。
作扫描线然后每次找前面第一个比之前答案还有小的,最多找 log 轮那个思路不太能套,树上怎么扫描线¿
搬分治的做法,点分治,然后找支配对。支配对数是 .
以后遇到序列上分治做的题目,就想想能不能搬到树上点分治搞,这样出题还挺好/cf
lxl 说是 codechef 某题 D
多组询问 .
支配对的套路。找出数量级比较小的点对使得答案一定会在它们当中取到。
枚举一个 ,考虑它作为后面那个 ,有用的 有哪些。枚举点对 的 LCA 的深度是 dep.考虑如果有两个位置 都合法,那么 深度一定更深,则 会更优。所以只有编号最大的那个 是有用的(当然大前提是 )。
换而言之,若此处有 :如果 只包含 ,那么就只有挑选出的支配对 有用,如果 包含了 ,在前面一定会有更优的。故而这样只跳出 个支配对,然后问题就变成了 2-side 问题了。
CF1446D2 D
全是重量级! 拉了,来看看 1log 和线性的做法。
遇到最优化题目或者什么的,先想想全局最优解是什么,能否用它来简化问题(P8511 TEST_68)在这里就发现全局众数一定是答案区间的众数之一。如果一个区间的众数不是全局众数的话,考虑左端点一步步往左扩,右端点一步步往右扩,在最后全局众数会超过之前的众数,那么一定存在某个时刻它们两个相等,从而得到了更长的合法区间。
也就是如果一个区间众数不是全局众数,那么一定存在一个更大的答案,假设众数是 ,枚举另一个众数 ,将 出现位置设成 , 出现位置设成 ,求个最长的和为 的区间。
思路是考虑如果暴力做是 的,如果 就寄了。但是考虑此时有很多 是一定不会用到的。具体而言,如果从这个 开始往后跑,前缀和都 ,并且往前跑也都是 ,那么这个 一定用不到。想想怎么找出有用的 !
先看往后跑,前缀和都 .用折线图思考这个东西,发现每次 会让它前面一个 合法.具体而言,对于每个 匹配上它前面最近的还没有被匹配的 .那么只有匹配成功的 是有用的。
反过来也一样,可以做同样的事情求个交,当然也可以接着上面那个继续跑。用 set 暴力实现是 的。
咋优化到线性?求交和最后统计都挺简单,问题就是对于每个 ,每次和它前面一个没被匹配的 匹配,求出所有被匹配的 .由于 是固定的,预处理出每个 前面第一个 和后面第一个 .
只看 的话,相当于初始全 的序列,每次查询某个位置前面第一个 ,然后将 置成 .但是 后面第一个 一定没有被删掉,所以其实是查询一个 前面第一个 ,那就用链表维护一下就可以了。找完之后记录一下链表咋改变的再回退即可。
复杂度被优化到了线性。
P6105 B or D?
先求个 ,考虑一下桶,下标之和 ,且 是个常数,套路就是反转其中一个,那就令 为桶, 为桶反转之后的结果,再适当右移一位,则相当于询问 ,动态开点线段树 卡空间 只能 平衡树维护分治信息。我谔谔,不知道能不能过,懒得写。
或者考虑一下会贡献给答案的最优匹配实际上是双向的,如果要 insert ,找一下 的最优匹配 ,如果没有这个 或者 ,那么 就是一个双向的最优匹配, insert 到堆里面。然后可能会破坏 原先的最优匹配,看一下 的最优匹配是否是 ,如果是的话再把 给删掉。
erase 也同理。把 insert 倒过来做就行。
CF453E A
没看明白题解区都是些啥。。。混乱。
先上个 set 维护颜色段,初始的那个特殊处理一下。现在问题变成了 次询问初始全 ,区间 在时间 时候的和,差分成 的减去 的。
扫描线扫序列维,在时间维上每次就是一个等差数列加和一个区间加。然后询问一个单点的和。对差分数组就是一个区间加 前缀和问题,上线段树就行。时间复杂度 .
/yiw B
从云浅那里看到的题:区间排序,区间求和。
先上个 set 维护连续段。然后每个连续段开棵值域线段树,线段树分裂 + 线段树合并,这样就能维护出每个连续段的总和。然后现在区间求和就是查询若干个连续段的和,还有一个连续段的后缀,一个连续段的前缀。
在 set 里定位一下连续段,后两个直接在值域线段树里查一下。前面那个连续段的区间和可以不写平衡树,一个连续段的值记在左端点上,用线段树维护之即可。时间复杂度 (忘了线段树分裂复杂度了,那就 统一成 算了。)
QOJ5098 D
明明应该是简单题的 ... 为什么想不出来!!
考虑一下不带修怎么做,原来是我的不带修做法做麻烦了。
考虑令 为右端点为 时最靠左的左端点,首先一定有 不降。那么询问 时,右端点 就分为 和 两种,二分一下分界线,前面的是 可以直接算,后面是 那就是区间最值。
现在带修了,先考虑咋维护 .对于一个 ,相当于将 的 均和 取个 ,那每次单点修改的时候就是扔掉若干个限制再加进来若干个限制,不能删除,但考虑一下只有插入还是很好做的,那就上一发线段树分治,用线段树维护 ,那后缀 也是线段树上二分一下会把哪段区间整体覆盖掉( 不降),那么 的区间最大值也是很好维护的了。
时间复杂度 .
P6864 B
怎么场上只有四个过的??
先考虑没有撤销操作,就是每次外套一对括号或者后加一对括号,考虑合法括号子串数 怎么变:
- 外套:;
- 后加:令 为整个串能被划分成多少个
(A)
这样的串拼接起来,然后 .
现在又需要维护一个 ,考虑 怎么变:
- 外套:;
- 后加:.
发现转移是线性的,那就写成矩阵的形式就可以了。线段树维护矩阵连乘积,这样也能支持撤销操作(也就是删除一个矩阵)。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?