集训总结(四)

9.9

P5522 棠梨煎雪

挑题的时候 qk 说这是线段树优化状压 dp,写完后看了看自己的代码,线段树?我怎么没有啊?状压 dp?我怎么没有啊?

考虑区间 \([l,r]\) 字符串每一位对答案造成的影响,设考虑到第 \(k\) 位:

1.第 \(k\) 位有 \(0\)\(1\):此时无论 \(S\) 是什么,都不可能有贡献,答案为 \(0\)
2.第 \(k\) 位有 \(0\)\(1\):此时 \(S\) 的第 \(k\) 位也只能是 \(0\)\(1\),答案不变。
3.第 \(k\) 位全为 \(?\):此时 \(S\) 的第 \(k\)\(01\) 均可,根据乘法原理,答案 \(\times 2\)

发现我们只需要维护区间某一位的 \(01\) 个数,于是我们对每一位的 \(0\)\(1\) 个数都单独开一棵树状数组,由于 \(n\) 很小,所以我们可以直接暴力枚举,判断当前位 \(0\)\(1\) 的个数即可。

复杂度 \(O(qnlogm)\) 但常数很小,没怎么卡就过了。

要永远相信树状数组的速度!!!

P7475 简易输入法

扫码了,卡我树套树空间。

对所有字符串建立字典树,跑一遍 \(dfs\),跑出 \(dfn\) 序,将树上问题转化为了序列问题,然后这就是一个裸的树套树板子了,直接上树状数组套权值线段树即可。

9.10

坏消息:模拟赛挂分了。
好消息:10元幸运奖抽到我了。

P2824 排序

发现直接排序有点难搞,考虑怎么转化。

发现我们只关心最终查询位置上的值,考虑对那个位置二分答案。设此时 \(check\) 的数是 \(k\),我们将所有大于等于 \(k\) 的数化为 \(1\),将所有小于 \(k\) 的数设为 \(0\),这样我们就将序列转化成了 \(01\) 序列。此时我们再看操作,相当于是找到区间 \(01\) 的分界点,然后区间推平,\(ODT\)/线段树维护一下就好了。

9.11

P13925 联合猫国

考虑 dp,枚举左端点 \(j\) 和右端点 \(i\),如果 \(i\)\(j\) 可以合并就 \(dp_j+1 \to dp_i\)

考虑固定 \(i\) 时如何快速枚举 \(j\)。注意到假设相邻两个合法的 \(j\) 分别为 \(k'\)\(k\),那么必有从 \(k'\)\(k−1\) 合法且这一段合并的结果与 \(k\)\(i\) 相等。

于是用一种类似倍增的方法,记录可以从哪里过来。容易发现这样复杂度是对的。最劣的情况大概是全相等的时候,转移次数 \(O(nlogn)\)

P2774 方格取数问题

题目的限制条件相当于选了一个数,四周的数就不能选。将每个点拆成入点和出点,初始从点 \(s\) 向入点连 \(a_{i,j}\) 的边,从出点向 \(t\)\(a_{i,j}\) 的边。对于每个点,四周的点不能选,就从这个点的入点向四周的出点连一条 \(inf\) 的边,之后跑最小割就可以了。

P2764 最小路径覆盖问题

最小路径覆盖=总点数-最大匹配。

跑匈牙利,记录一下每个点的前驱就可以了。

posted @ 2025-09-09 11:35  leizepromax  阅读(11)  评论(0)    收藏  举报