2023 暑假集训模拟赛题解
目录
CSP 模拟 1
CSP 模拟 2
F
考虑 \(x\) 只能在 \(a_1\oplus b_i\) 里选,那么分别代入暴力检验即可 .
时间复杂度 \(\tilde\Theta(n^2)\),可以通过 .
S
考虑交换同色的部分一定不优,所以同色字符的相对位置一定不变 . 那么操作序列和最终局面肯定是能形成双射的 .
于是只需要考虑计数最终局面,设计一个 DP,令 \(dp_{i,j,k,c}\) 表示三种颜色分别选了 \(i,j,k\) 个,第 \(i+j+k\) 位是 \(c\) 的最小步数 .
根据前面的分析,最小步数其实就是序列的「逆序对」个数,维护每个颜色的位置和每个位置前面颜色的个数即可计算贡献 .
时间复杂度 \(O(n^3)\),需要滚动数组以将空间复杂度优化到 \(O(n^2)\) .
Y
原题:ARC124E Pass to Next .
对于操作序列 \(\{x_n\}\),可以发现如果能减的话给每个元素都减一得到的最终局面不变 . 称满足 \(\min x_i=0\) 的操作序列 \(\{x\}\) 为素操作序列,那么可以发现素操作序列和最终局面之间是存在双射的,于是只需要计算素操作序列个数 .
考虑容斥计算,即算出 \(x_i\in[0,a_i]\) 的权值和减 \(x_i\in[1,a_i]\) 的权值和 . 做法本质相同,下面以前者为例 .
首先大力写出答案:\(\displaystyle\prod_{i=1}^n(a_i-x_i+x_{i-1})\) . 那么一项一项选就行了:
- 如果选 \(a_i\),那么这一位的贡献即为 \(a_i\) .
- 如果选 \(-x_i\),那么这一位的贡献即为 \(-x_i\),表现出来是一个等差数列求和的形式 .
- 如果选 \(x_{i-1}\),如果上一位选的是 \(x_i\) 那么贡献表现为平方和,否则表现为等差数列求和 .
由于有一个上一位的限制那么开一个状态机 DP 表示就好了,具体的,维护:
然后提出 \(\prod\) 内的一项考虑转移即可 .
最后,因为是环状结构所以需要破开然后钦定断点处的选择方案 . 时间复杂度 \(\Theta(n)\),可以通过 .
O
原题:JOI 2020 Final 火事 .
考虑每个点的影响写成四元组 \((p,t,t',d)\) 的形式,表示从 \(p\) 位置,\(t\sim t'\) 时刻,产生 \(+d\) 的贡献 .
对于一次询问,拆成两个前缀和相减,假设目前询问是 \((x,i)\) 表示查 \(i\) 时刻的前缀和 \(1\dots x\),那么写出来贡献就是:
由于询问部分和操作部分独立了,所以按 \(i\) 扫描线,\(p-t,p\) 开下标上里面记贡献,然后统计的时候就是区间求和了,线段树即可 . 时间复杂度 \(O((n+q)\log n)\),可以通过 .
但是学校 OJ 卡常,卡了半天才过去 . 可能是我的实现不太好吧 .
CSP 模拟 3
回文
考虑从左上和右下一起走到中间会合,整一个 DP 就好了,因为步数一样所以可以省一维 .
时间复杂度 \(\Theta(n^3)\),可以通过(假设 \(n,m\) 同阶).
快速排序
可以发现过程实际上就是如果第一个数 \(x\) 是 nan 那么往右递归否则把 \(<x\) 的数全移到左边然后递归 .
冷静一下可以看出来每次实际上只有往右递归是必要的,那么直接暴力,均摊下来复杂度就对了 .
总时间复杂度 \(O(n\log n)\),可以通过,瓶颈在排序 .
混乱邪恶
确实混乱邪恶 .
首先在序列末尾补 0 直到长度为偶数,那么令 \(\{a\}\) 的长度为 \(2n\),排序后构造 \(d_i=a_{2i+1}-a_{2i}\),那么只要能构造出 \(\{e\}\) 满足 \(\sum d_ie_i=0\) 就可以进而构造出 \(\{a\}\) 的方案了 .
因为 \(a_i\) 都互不相同,\(d_i\) 相当于相邻 \(a_i\) 的距离,那么可以得到 \(\sum d_i\le m-n<2n\)(注意这里 \(2n\) 是原题的 \(n\),所以对 \(m\) 的限制事实上是 \(\lfloor\frac{m}3\rfloor<n\le\lfloor\frac m2\rfloor\)).
抽象问题为正整数序列 \(\{d_n\}\) 满足 \(\sum d_i\) 是小于 \(2n\) 的偶数,构造一组仅含 \(1,-1\) 的序列 \(\{e_n\}\) 使得 \(\sum d_ie_i=0\) .
考虑数学归纳法,如果 \(n=1\) 那么必然 \(d_1=0\),不用构造 . 如果 \(\{d\}\) 中所有元素全相等那么交错构造即可(看起来如果 \(n\) 是奇数的话可能构造不出来,但是如果 \(d\) 中元素都是奇数则不满足和是偶数的限制,如果 \(d\) 中元素都是偶数那么至少全是 2 不满足和小于 \(2n\) 的限制).
对于任意序列 \(\{d\}\),取出最大值和最小值 \(\max,\,\min\),构造新序列 \(\{d'\}\) 由 \(\{d\}\) 删除 \(\max,\,\min\),加入 \(\max-\min\) 得出,那么如果 \(d'\) 能构造则 \(d\) 也能简单构造 .
注意到 \(d'\) 的和减少 \(2\min>0\),且长度变为 \(n-1\),那么变为规模更小的子问题,根据归纳假设肯定有解 .
那么按照过程递归下去构造就好了 . 这里每次取最值可以保证下一次构造出现 0 的时候肯定最大值等于最小值可以直接结束 .
实现细节:构建一棵二叉树,每个结点 \(u\) 上维护两个指针 \(l,r\),表示点权 \(\operatorname{value}(u)=\operatorname{value}(l)-\operatorname{value}(r)\),那么每次递归的时候把 \(\max-\min\) 提出来连 \(\max,\,\min\),统计的时候 DFS 下去就可以了(做法来自 sandom).
时间复杂度 \(O(n\log n)\),可以通过 .
校门外歪脖树上的鸽子
对于一颗二叉树 \(\mathcal T\),定义 \(\operatorname{mirr}(\mathcal T)\) 由如下流程生成:定义 \(\operatorname{side}(u)\) 为 \(u\) 是否是 \(u\) 父亲的左儿子,\(c(u)\) 为 \(u\) 的祖先中第一个 \(\rm side\) 和 \(u\) 不一样的结点的兄弟,则 \(\operatorname{mirr}(\mathcal T)\) 上有边 \(u-c(u)\) .
对于一条二叉树上的直链 \(u-v\),定义其「虫足」为 \(u\) 到 \(v\) 每个非链底点的不在链上的儿子组成的集合,那么可以发现对于 \(\mathcal T\) 上一条直链,其同侧虫足一定在 \(\operatorname{mirr}(\mathcal T)\) 上处于同一条直链 .
如果原二叉树为 \(\mathcal T\),那么可以注意到的是,一次修改操作影响的点实际上在 \(\operatorname{mirr}(\mathcal T)\) 上表现为两条直链(有一些 corner case 需要特殊处理一下). 查询操作的范围是一致的 . 那么问题变成了链加链和,树剖维护即可 .
时间复杂度 \(O((n+q)\log^2n)\),可以通过 .
详细说明 .
CSP 模拟 4
最长上升子序列
原题:ARC125C LIS to Original Sequence .
观察可以发现排列肯定形如 \(a_1,R_1,a_2,R_2,\cdots,a_n,R_n\),其中 \(R\) 是单调减的序列且 \(R_i\) 的元素在 \(a_i\) 和 \(a_{i+1}\) 之间 .
那么 \(R_1,R_2,\cdots,R_{n-1}\) 取能取的最小的一个数,\(R_n\) 放其余的数即可 .
时间复杂度 \(O(n)\),可以通过 .
独特序列
原题:ARC125D Unique Subsequence .
子序列自动机 DP 基础题,和本质不同子序列做法差不多,令 \(dp_n\) 表示以 \(n\) 结尾的只出现一次的子序列个数,那么:
其中 \(\operatorname{last}(x)\) 表示 \(x\) 上一次出现的位置,转移过后要删除 \(dp_{\operatorname{last}(a_n)}\) 的贡献,即令 \(dp_{\operatorname{last}(a_n)}\gets0\) .
用树状数组优化即可做到 \(O(n\log n)\),可以通过 .
最大 GCD
原题:ARC126C Maximize GCD .
对于一个 GCD \(d\),当且仅当满足
时 \(d\) 可以作为一个合法解 .
如果 \(d>\max a_i\) 那么 \(d\le\left\lfloor\dfrac{k+\sum a_i}n\right\rfloor\) 所以如果 \(\left\lfloor\dfrac{k+\sum a_i}n\right\rfloor>\max a_i\) 则答案为 \(\left\lfloor\dfrac{k+\sum a_i}n\right\rfloor\) .
那么剩下的情况必有 $d\le\max a_i $,只需要快速对所有 \(d\) 计算 \(\displaystyle\sum_{i=1}^n\left\lceil\dfrac{a_i}d\right\rceil\) 即可 .
令 \(\displaystyle G(x)=\sum_{i=1}^n[a_i\ge x]\),那么不难发现 \(\displaystyle\sum_{i=1}^n\left\lceil\dfrac{a_i}d\right\rceil=\sum_{i\ge 1}G(1+di)\) .
\(G\) 可以通过在值域上前缀和求出,后者的时间复杂度可以由调和级数分析,那么问题被以 \(O(v\log v)\) 的时间复杂度解决,其中 \(v\) 是值域,可以通过 .
连续子段
考虑形成最终连续段的过程分为两部分:将最终的元素凑到一起和将元素冒泡排序 .
称最终连续段内的元素为最终点,那么考虑把最终点凑到一起的贡献在非最终点处计算,每次最终点只计入冒泡排序的贡献,即目前逆序对 .
那么令 \(dp_{n,S}\) 表示 \(1\dots n\) 选了标记点集 \(S\) 的最少步数,那么讨论最后一个是否选最终点即可转移(对于非最终点,考察它至少需要经过多少个最终点).
时间复杂度 \(\Theta(n2^k)\),可以通过 .
CSP 模拟 5
第一题
贪心地按子树深度从小到大遍历即可 .
时间复杂度 \(O(n\log n)\),可以通过,瓶颈在排序 .
第二题
起手二分答案,然后考虑用类似 SPFA 的东西判断 .
首先把所有点都放到队列里,每次拿出队头扫描邻接点,将队头更改到最大值附近,然后再次扫描邻接点计算贡献并入队就好了 .
时间复杂度 \(O(\text{能过})\),显然可以通过 .
第三题
比较奇怪的数位 DP,令 \(dp_{i,j,l,r}\) 表示填到第 \(i\) 位目前有 \(j\) 个 1,当前数是否顶格(上界、下界).
那么每个状态维护方案数和数字和即可完成转移 . 求出 DP 数组后 \(k\)-th 可以用类似线段树二分的方法求 .
时间复杂度 \(\Theta(\log^2 n)\) . 好像 3log 大力做法也能过 .
第四题
令 \(f_{i,j}\) 表示选 \(i\) 个数最大值为 \(j\) 的方案数,\(g_{i,j}\) 表示最大值为 \(j\) 的序列后面接 \(i\) 个数的方案数,那么可以转移:
由于 \(x^2=2\binom x2+x\),那么考虑强制一个数出现两次,讨论前面的 max 可以得到 \(x\) 在 \(i\) 位置第一次出现的贡献为:
前缀和优化就是 \(\Theta(n^2)\) .
CSP 模拟 6
排序
(几乎)原题:CF1375E Inversion SwapSort .
因为每次交换要保证尽量不影响逆序对,所以考虑每次只交换值上相邻的两个数,于是考虑求出原排列 \(\pi\) 的逆 \(\pi^{-1}\),不难发现在 \(\pi\) 上的逆序对在 \(\pi^{-1}\) 上仍是逆序对,于是对 \(\pi^{-1}\) 做冒泡排序后逆回来即可 .
对于 CF1375E,把每个 \(a_i\) 换成 \((a_i,i)\) 后离散化即为上述题目 .
时间复杂度 \(\Theta(n^2)\),可以通过 .
Xorum
原题:CF1427D Xum .
考虑每次消掉 highbit,因为 \(x\) 是奇数所以最后肯定能消成 1 . 令 \(h=\operatorname{highbit}(x)\) .
将 \(x\) 向左平移使得新数的 lowbit 和原数的 highbit 对齐,记得到的数为 \(y\) . 那么计算 \(z=x\oplus y\) 即可让第 \(h\) 位变成 \(0\),进而计算 \((z+y)\oplus(2y)\oplus x\) 即可得到 \(2^{h+1}\)(可以手玩一下),那么可以用这个 \(2^{h+1}\) 依次异或 \(z\) 的每个 \(h\) 以上的位,就得到 \(x\) 去掉 highbit 的值了,于是问题被变成了更小的子任务,递归下去做就行了 .
操作次数为 \(O(\log^2 x)\),可以通过 .
有趣的区间问题
原题:CF1609F Interesting Sections .
纯套路题,这种东西无非就是扫描线或分治,考虑一下分治 .
cdq 分治,那么只需要考虑跨越中点的贡献,双指针维护,扫一遍左边那么右端点可以分为三段:
- min, max 都由左边贡献:直接统计即可 .
- min, max 恰有一个由左边贡献:考虑两个端点动的时候开一个桶动态维护其前缀每个 popcount 出现的次数,查询的时候差分即可 .
- min, max 都由右边贡献:对右边的前缀 min, max 相等的部分计算后缀和统计即可 .
可以类双指针维护右边三段的分界点,那么问题被 \(\Theta(n\log n)\) 或 \(\Theta(n\log n\log v)\) 解决,可以通过 .
无聊的卡牌问题
对于每张卡,如果它是先手拿的,那么染 0,否则染 1 . 于是类似括号匹配,扫一遍每张卡,用一个栈动态维护,如果栈顶凑成三张同色卡了,就弹出来,这样任意时刻满足栈里上面的元素必须比下面的先选,从而可以知道每组卡选取的先后关系 .
建出一棵森林来之后就变成每个点有点权,每次删叶子且要求最终序列 01 交错 .
不难发现这棵森林满足父亲和儿子颜色不同且 0 和 1 的数量相等,于是拓扑排序随便删叶子,注意最后删的必须是一个颜色为 1 的根就好了 .
关于正确性证明,只需要证明有解状态能转移到的都是有解状态即可:
- 假设目前要取颜色为 0 的叶子,那么此时 01 数量相同 . 假设选一个 0 后没有 1 叶子了,那么这个状态满足 1 比 0 多一个,且有一个 1 根 . 因为没有为 1 的叶子,所以每个 1 至少有一个 0 儿子,这与 1 比 0 多矛盾 .
- 假设目前要取颜色为 1 的叶子,类似证明,假设选一个 1 后没有 0 叶子了,此时 01 数量相等,因为没有 0 叶子所以每个 0 至少有一个 1 儿子,且根是 1,这与 01 数量相等矛盾 .
时间复杂度 \(\Theta(n)\),可以通过 . 因为 \(n\) 非常小所以某些地方写的比较大力也是可以过的 .
然而学校 OJ 暴搜记忆化就可以过了,详见 5k_sync_closer 大神 . 拜谢 .
CSP 模拟 7
卷
取对数维护大小关系之后变成朴素最大权独立集问题,树形 DP 即可 .
时间复杂度 \(\Theta(n)\),可以通过 .
简单题
对于任意正整数 \(n\) 连边 \(n-2n\),那么就变成算这张图的黑白染色方案数 . 不妨令黑点为集合 \(A\) 中元素 .
可以发现图的最终形态肯定是若干条链 \(n-2n-\cdots-2^kn\),其中 \(n\) 是奇数 . 那么对于长为偶数的链来说,染色方案是不会影响黑色点数量的 . 对于长为奇数的链来说,减掉必须有的点数后就变成一个组合数的形式 .
因为链的长度是 \(O(\log n)\) 级别的,所以考虑对于每种链的长度计算满足条件的链数量,后面就好算了 .
时间复杂度 \(O(p+\log n+q\log_pn)\),其中 \(n,m\) 同阶,\(p\) 是模数 . 可以通过 .
粉丝
差分变成有下界的分拆数,因为模数有点逆天 GF 方法比较难整,所以考虑根号分治做法 .
对于这个问题可以编两个 DP,首先令 \(dp_{n,k}\) 表示序列最大值为 \(n\) 和为 \(k\) 的方案数然后直接转移即可(完全背包).
另一方面,设下界是 \(b\),可以令 \(dp_{n,k}\) 表示选了 \(n\) 个数和为 \(k\) 的方案数,考虑所有合法序列可以由若干次开头接一个 \(b\) 和全局加一构造,那么可以转移:\(dp_{i,j}=dp_{i,j-i}+dp_{i-1,j-b}\),后面把这个 DP 记作 S .
注意到第一维最大只能到 \(\frac nb\),于是 S 的时间复杂度实际上是 \(\Theta(\frac{n^2}b)\),前面那个完全背包显然是 \(\Theta(nb)\) .
那么对于 \(b>\sqrt n\) 跑 S,\(b\le\sqrt n\) 小的部分跑完全背包、大的部分跑 S,最后拼起来就可以了 . 时间复杂度 \(O(n\sqrt n)\),可以通过 .
字符串
注意到可以每次删一个开头字符删一个结尾字符,那么 \(A,E\) 中肯定有一个被删空了,那么问题就变成把字符串 \(S\) 分成四部分 \(S=A+B+C+D\),使得 \(A+C\) 或 \(B+D\) 是回文串且长度尽可能大,不妨讨论 \(A+C\):
- 回文中心在 \(A\) 上,枚举回文中心用 manacher 求出回文半径,假设目前的回文串是 \([l,r]\),那么只需要考虑有没有一个 \([1,l)\) 前缀的逆序在后面出现过,把原串翻转接在 \(S\) 后面(中间需要放一个分隔符),那么就是一个前缀最大 border 的后缀 max,跑 KMP 即可 .
- 回文中心在 \(C\) 上,类似,枚举回文中心然后 manacher 求回文半径,剩下部分 KMP .
时间复杂度 \(\Theta(n)\),可以通过(带 log 的应该过不去吧).
CSP 模拟 8
Coprime 2
原题:ABC215D Coprime 2 加强版 .
对于每个素数 \(p\),暴力跳一遍查询是否有一个 \(a_i\) 是它的倍数,如果有就标记所有 \(p\) 的倍数 . 不难发现没被标记的所有数即为答案 .
根据 Mertens 第二定理时间复杂度为 \(\Theta(v\log\log v)\),\(v\) 是值域 . 可以通过 .
Dist Max 2
原题:ABC215F Dist Max 2 .
查邻域没前途 . 考虑二分答案 \(k\),那么对 \(x\) 排序后双指针即可限制 \(|x_i-x_j|\ge k\),对于满足条件的区间查最值即可知道是否有满足条件的 \(|y_i-y_j|\ge k\) .
时间复杂度 \(\Theta(n\log v)\),\(v\) 是值域,可以通过 .
Count Multiset
有点套路,令 \(dp_{i,j}\) 表示长为 \(i\) 和为 \(j\) 的方案数,考虑后面接一个 1 或者全局加 1 构造所有数列,关于重复元素不超过 \(m\) 的限制容斥即可 . 具体转移:
最后一项相当于容斥掉开头恰有 \(m+1\) 个 1 的方案数 .
直接算,时间复杂度 \(\Theta(n^2)\),可以通过 .
Julia the snail
离线扫描线,需要对于每个右端点计算左端点的答案 . 考虑右端点移动一次对于每个左端点答案的影响,令目前右端点 \(r\) 对应一条绳子 \([l,r]\),对于原来答案为 \(x\) 的左端点 \(i\),如果 \(x\ge l\) 那么新的 \(x\) 就会变成 \(r\) .
那么可以发现只需要动态维护一个序列 \(\{a\}\),支持:
1 l r
,对于 \([1,l]\) 中每个满足 \(a_i\ge l\) 的 \(i\),令 \(a_i\gets r\) .2 u
,查询 \(a_u\) 的值 .
这种限制值域的修改可以考虑 seg-beats 维护,具体的,维护变换 \((x,y)\) 表示 \(\ge x\) 的数全都改成 \(y\),剩下的部分和常规 seg-beats 一样 . 时间复杂度 \(O((n+q)\operatorname{polylog}(n))\),听说实际上是 1log,我不会势能分析就先摆了 .
注意模拟赛的数据有问题,\(r_i\) 不一定互不相同,注意一下 .
CSP 模拟 9
最短路
原题:USACO09DEC Cow Toll Paths G .
考虑钦定最短路上点权最大的点 . 注意到 Floyd 实际上是一个三维 DP,\(dp_{i,j,k}\) 表示只用 \(1\dots k\) 中的点 \(i-j\) 的最短路,那么按点权排序后 Floyd 可以自然维护当前点权的最大值 . 从而做 Floyd 即可 .
时间复杂度 \(\Theta(n^3)\),可以通过 .
方格取数
原题:POI2008 KUP-Plot purchase .
(下面做法口胡得到,不保证完全正确)
首先删掉所有比 \(2k\) 大的数,如果有数在 \([k,2k]\) 之内那么它本身就是一组解 . 那么现在只剩下小于 \(k\) 的数了,断言:如果存在一个子矩阵和 \(>2k\),那么其必然存在一个子矩形和在 \([k,2k]\) 间 .
关于证明,考虑最后一列的和 \(S\):
- 如果 \(S<k\),那么把最后一列删了变成子问题 .
- 如果 \(k\le S\le 2k\),\(S\) 就是一组解 .
- 如果 \(S>2k\),因为每个数都在 \([k,2k]\) 间,所以一个一个删总会有一个在 \([k,2k]\) 间的子矩形 .
从而,找到不含 \(2k\) 的最大子矩形后按如上方法构造即可,时间复杂度 \(\Theta(nm)\),可以通过 .
数组
原题:CF1114F Please, another Queries on Array? .
考虑欧拉函数关于素因子的表达式 \(\displaystyle\varphi(n)=n\prod\dfrac{p_i-1}{p_i}\),那么对于 \(n\) 那一项直接朴素线段树维护 . 后面的肯定是对于每个素因子考虑,然后变成区间推平,不过常数有点大,无法通过 . 不过注意到值域 \(v=300\) 之内只有 \(61\) 个素数,可以压到一个 word 里变成区间或,这样就能过了 .
时间复杂度 \(O(\frac{\pi(v)}w(n+q)\log n+(n+q)\pi(v))\),可以通过 .
树
原题:POI2015 ODW .
根号分治 .
对于步长 \(c\le\sqrt n\),对于每个 \(c\) 处理 \(c\) 一直跳到根的点权和(这里也能顺便处理出每个点的 \(1\dots\sqrt n\) 级祖先),询问时树上差分即可 .
对于步长 \(c>\sqrt n\),可以发现跳的次数不超过 \(\sqrt n\) 可以考虑暴力跳,类似 BSGS,将一个树上 \(c\) 级祖先分成若干个 \(\sqrt n\) 和一个散的,不难发现这样做时间复杂度为 \(O(n\sqrt n)\) .
不算求 LCA 时间复杂度为 \(O((n+q)\sqrt n)\),可以通过 . 在线非长剖做法,好 .
CSP 模拟 10
Because / Love / yoU / Everyday .
B
签到 .
L
原题:Simple Set Problem .
先把所有数加上下标排好序放到一起,那么扫描线统计所有颜色都有的时候的贡献即可 .
不算排序时间复杂度 \(\Theta(\sum c_i)\),可以通过 .
U
原题:WO MEI K .
对于每个点 \(u\),设其父边的边权为 \(w\),考虑计算 \(u\) 子树内每个边权为 \(w\) 的子树权值都不计算的方案数,dsu on tree 或者按 DFS 序动态加减贡献即可 .
考虑每条边 \((u,v)\) 的贡献 . 对于 \(u\) 子树内的,直接用预处理出来的值算即可 . 对于子树外的,找到 \(v\) 到根路径上最近的和其边权相同的边后面就和子树内情况一样了,需要特殊处理不存在这样的边的情况 .
时间复杂度 \(\Theta(n)\) 或 \(O(n\log n)\),可以通过 .
E
码农题,蚌 .
注意到数据随机,可以猜想最终答案肯定能表为 \(\Theta(1)\) 个区间的并,那么线段树维护即可 . 合并可以用扫描线完成 .
时间复杂度 \(O((n+q)\log n)\),可以通过 .
CSP 模拟 11
原
原题:51nod 1232 完美数 .
直接考虑数位 DP 即可,需要额外维护当前包含数字集合的 LCM 和当前数模 LCM 的值 .
因为 LCM 的模数总变比较麻烦,注意到 LCM 永远是 \(\operatorname{lcm}(1,2,3,\cdots,9)=2520\) 的因子,所以改成模 \(2520\) 即可 .
需要进行一些优化,然后就可以过了 .
神
原题:CF163E e-Government .
首先建 AC 自动机,那么考虑 fail 树就是单点加,查询一个点到根的点权和 .
用一个树上差分就变成了子树加单点查询,DFS 序上树状数组即可维护 .
时间复杂度 \(\Theta(m\log m)\),\(m\) 是 AC 自动机大小 .
启
注意到选 \((a_i,b_i)\) 对差的贡献是 \(a_i+b_i\),那么按 \(a_i+b_i\) 排序后轮流选即可 .
时间复杂度 \(O(n\log n)\),可以通过 .
动
原题:CF932F Escape Through Leaf .
首先有朴素 DP:
考虑优化,两种想法:
-
相当于维护若干条直线 \(y=b_j\cdot x+dp_j\) 找某处最大的点值,李超线段树维护即可 .
-
斜率优化,写成 \(dp_j=-a_i\cdot b_j+dp_i\) 的形式 .
那么需要维护凸包,用 set 或者平衡树即可 .
都可以实现到线性对数时间复杂度,不过如果第二种想法用 set 只能启发式合并就是 \(O(n\log^2n)\) 了 .
CSP 模拟 12
随
不难发现每个点最后是本身的概率都是一样的,那么只需要求一个位置的概率就好了 .
令 \(p_m\) 为操作 \(m\) 次后某个位置不是本身的概率,则不难导出递推:
解出来就好了(OGF 或差分).
时间复杂度 \(\Theta(T\log p)\),\(p=998244353\) 是模数,可以通过 . log 来源于快速幂 .
便
原题:HDU7294 Hello World 3 Pro Max .
朴素 DP:令 \(dp_{i,j}\) 表示当前字符串长度为 \(i\),匹配到 helloworld
的第 \(j\) 位时的期望次数,转移略 .
写成矩阵形式后用线段树优化即可,时间复杂度 \(O(n+q\log n)\),可以通过 .
需要大力卡常,一些技巧:
- 因为转移矩阵是上三角矩阵,所以矩阵乘的时候可以直接丢掉几乎一半的数 .
- 矩阵乘法最后取模 .
- 线段树查询时用一个全局变量每次复合叶子结点维护的值 .
A
考虑区间 DP,令 \(dp_{l,r,x,k}\) 表示 \([l,r]\) 内的卡最终合出来一张等级为 \(x\) 种类为 \(k\) 的卡的最大收益,\(t_{l,r}\) 为打完 \([l,r]\) 中的卡的最大收益,那么可以转移:
时间复杂度 \(O(n^3mr)\),小常数,可以通过 .
C
(几乎)原题:AGC017D Game on Tree .
首先考虑根固定怎么做,也就是那个 AGC 题的做法 .
注意到,对于一个点 \(u\) 的子树,把 \(u\) 拆成若干个点分给每个儿子,然后断掉根,这样可以得到若干个独立的游戏,并且整体的 SG 相等 .
那么对于每个游戏,都是子树上面接一条边,不难发现这个的 SG 是原子树的 SG 值加一 .
从而,令 \(\operatorname{sg}(u)\) 表示 \(u\) 子树的 SG,那么有递推:
求每个根的值只需要换根即可 . 算出每个值之后加起来除以 \(n\) 就是最终的答案了 .
时间复杂度 \(\Theta(n)\),可以通过 .
CSP 模拟 13
y
xt 肯定是选四个角,对于每个点算离四个角距离的最大值然后排序即可 .
时间复杂度 \(O(nm\log nm)\),可以通过 . 复杂度瓶颈在排序 .
s
考虑算答案 \(\ge x\) 的排列的个数然后加起来,那么让 \(\ge x\) 的数为 1,否则为 0,于是令 \(dp_{i,j,0/1}\) 表示长度为 \(i\) 的 01 串,有 \(j\) 个 1,最后答案是 \(0/1\) 的方案数,答案就是:
关于 \(dp\) 数组,可以朴素 DP 解决,那么直接计算即可,时间复杂度 \(\Theta(n^2)\),可以通过 .
p
结论:对于两个点集,其并的直径端点必然是两个点集中的直径端点 .
证明并不困难,下简述思路:
反证,考虑点集 \(U,V\) 的并,只需要考虑新直径的端点分别在 \(U,V\) 的答案即可,设 \(U,V\) 直径端点连起来得到 \(u_0-v_0\),真正的直径是 \(u-v\),注意到距离某个点最远的点一定是直径端点,所以 \(u-u_0\) 是整棵树中从 \(u\) 出发的最远的点,因为 \(u,u_0\in U\) 且 \(u\) 是直径端点,所以 \(u_0\) 也是 \(U\) 中的直径端点,矛盾 . 证毕 .
那么线段树维护即可,实现优秀的话时间复杂度是 \(O((n+q)\log n)\) 的,可以通过 .
m
后面「合法」针对第二个条件 . 首先二项式反演,令 \(f(n)\) 表示钦定 \(i\) 个元素不合法的方案数,那么答案就是:
对于 \(f\) 来说,选的方法肯定是 \(2^{2^{n-i}}\) 种,后面枚举分成多少个集合可以得到:
后面的组合意义比较鲜明,整一个 DP 即可,具体的:
前一项是钦定最后的元素放在某个集合,后一项是随便放 .
那么直接算就是 \(\Theta(n^2)\) 了,可以通过 .
CSP 模拟 14
第负一题
原题:洛谷 P7482 不条理狂诗曲 .
cdq 分治,那么只需要考虑跨越中点 \(m\) 的贡献 .
令 \(f_{x,0/1}\) 表示考虑 \(x\dots m\),不选 / 选 \(m\) 的答案,\(g_{x,0/1}\) 表示考虑 \(m+1\dots x\),不选 / 选 \(m+1\) 的答案,则区间 \([l,r]\) 的答案就是 \(\max(f_{l,0}+g_{r,0}, f_{l,1}+g_{r,0}, f_{l,0}+g_{r,1})\) .
考虑分离两类变量,答案可以改成 \(f_{l,0}+g_{r,0}+\max\{\max\{f_{l,1}-f_{l,0},0\},\max\{g_{r,1}-g_{r,0},0\}\}\) .
左边的贡献是容易处理的,对于右边,处理 \(F_i=\max\{f_{i,1}-f_{i,0},0\},\ G_i=\max\{g_{i,1}-g_{i,0},0\}\),放到一起排序后就好算了 .
时间复杂度 \(O(n\log^2n)\),可以通过 .
Kaguya 表示她有一个线性做法,放个链接先 .
数树
对于一条边 \((u,v)\),如果 \(a_v=a_u+1\) 那么称其为不合法的,那么不难发现不合法边构成若干条链 .
考虑类似二项式反演,求出选钦定 \(i\) 条边不合法的方案数,然后容斥算出恰有 0 条不合法边的 .
令 \(dp_{u,k,0/1/2/3}\) 表示 \(u\) 子树内选 \(k\) 条边,\(u\) 结点没连边 / 连了内向边 / 连了外向边 / 连了内向边和外向边的方案数,那么转移类似树上背包,不是很困难就不说了 .
最后放一下答案:\(\displaystyle\sum_{i=0}^{n-1}(-1)^i(n-i)!(dp_{1,i,0}+dp_{1,i,1}+dp_{1,i,2}+dp_{1,i,3})\) .
时间复杂度 \(\Theta(n)\),可以通过,希望大家做题愉快 .
石子游戏
为了方便,令 \(x\gets x+1\) .
断言:后手必胜当且仅当 \(\displaystyle\bigoplus_{i=1}^n(a_i\bmod x)=0\) . 其实就是 Bash 游戏拼起来,有点朴素 .
那么套路地把取模拆了:\(\displaystyle\bigoplus_{i=1}^n\left(a_i-x\left\lfloor\dfrac{a_i}x\right\rfloor\right)\),只需要求这个就行了 .
先拆位,假设目前考虑到第 \(b\) 位 . 对于每个 \(x\),考虑每个段 \([kx,(k+1)x)\) 的贡献 . 对于段 \([l,r]\),找到 \(pos=\mathop{\rm arg\ max}\limits_{x=l+k\cdot2^{b+1}}\{x\le r\}\),那么把区间分成 \([l,pos]\) 和 \([pos+2^b,r]\)(中间那段肯定没贡献),右边可以简单统计,只需要考虑左边 .
令 \(dp_{i,j}\) 表示所有 \(a_k-i\) 第 \(j\) 位上 1 的个数,可以简单转移:
其中 \(c_k\) 是 \(\{a\}\) 中 \(k\) 出现的次数 .
这样就可以算左边了,注意到 DP 状态里含一个 \(a_i\ge i\) 的条件,直接用 \(dp\) 数组差分即可 .
时间复杂度 \(\Theta(n\log^2n)\),可以通过,有一个好剪枝是如果当前位异或和已经是 1 了那么直接跳出 .
子段和
估计我是没有希望做出来了 .
CSP 模拟 15
The Morning Star
签到 .
Ntarsis' Set
原题:CF1852A Ntarsis' Set .
考虑对于每个数,一次删除导致的某个位置的排名降低是可以轻易计算的 . 又因为答案有单调性,所以二分就可以了 .
时间复杂度 \(\Theta((n+k)\log nk)\),可以通过 .
Team Work
原题:CF932E Team Work .
做法还是比较多的,放一个最新看到的做法:
递推,第二维每次必减一,时间复杂度 \(\Theta(k^2)\),可以通过 .
Make Equal
原题:CF1188D Make Equal .
把 \(\{a\}\) 升序排序,假设最后把所有数都改成 \(m+a_n\),那么代价就是:
令 \(b_i=a_n-a_i\),那么按位考虑设计一个 DP,需要记录 \(m,b_i\) 对应位的值和进位的信息 .
进位比较难整,但是注意到每次加的数是一样的,所以假设目前考虑到 \(2^k\) 位,按 \(b_i\bmod 2^k\) 降序排序后肯定是一个前缀进位,这样就只需要记一个数了,时间复杂度 \(O(n\log n\log v)\),\(v\) 是值域,可以通过 .
CSP 模拟 16
糖果
不难发现如果全局异或和为 0 那么肯定可以划分成偶数段,否则每段的异或和必然为全局异或和,贪心划分即可 .
时间复杂度 \(\Theta(n)\),可以通过 .
魔法仪式
cdq 分治双指针就行了 .
时间复杂度 \(O(n\log n)\),可以通过 .
独特的数字
数位 DP 板子题,和 haha 数差不多 . 第二种询问需要再套个二分 .
时间复杂度 \(\Theta(T\log^2r)\) 可以通过 .
约会
先对于每个点 \(u\) 处理出 \(1-u\) 的最短路和 \(u-n\) 的最短路 .
考虑二分答案 \(w\),那么如果一个点可以随时在 \(w\) 时间内到达 \(n\) 则称其为好点,类似定义好边 . 那么可以发现如果 \(\operatorname{dist}(1,u)+\operatorname{dist}(u,n)\le a+w\) 那么 \(u\) 肯定是好点 .
其次,如果 \(u\) 是好点且 \(w(u,v)+\operatorname{dist}(v,n)\le w\),那么 \(v\) 是好点,\((u,v)\) 是好边 .
考虑下界 \(b\) 的要求,如果好边形成一个环,那么肯定 \(w\) 是合法的 . 否则,需要处理每个点能游走的最长时间,因为图是 DAG 所以直接在其上 DP 即可 .
要保证任意时刻都能出发,需要连一个 1 的自环 .
时间复杂度 \(O((n+m)\log m\log v)\),可以通过 .
CSP 模拟 17
NOIP 联测 35(密码是 accoders 端口号).
可能以后会补一份全题解 .
CSP 模拟 18
站队
对于每个连通块,随便搜出一棵生成树,固定一个点的位置然后即可算出其它点的位置,之后对于每个非树边检验即可 .
时间复杂度 \(\Theta(n+m)\),可以通过 .
打怪兽
原题:CF1852C Ina of the Mountain .
考虑原序列的差分 \(\{d\}\),那么问题变成找一个绝对值之和最小的序列 \(\{t\}\),满足:
- \(\{t\}\) 的任意前缀和不大于 0 .
- 对于每个 \(i\),有 \(k\mid d_i+t_i\) .
用反悔贪心处理,每次能放正的尽量放正的,如果不能放了看看能不能把前面的正的改小使其满足条件 .
时间复杂度 \(O(n\log n)\),可以通过 .
不用斯特林数
原题:CF585E Present for Vitalik the Philatelist .
令 \(S_i\) 为 GCD 等于 \(i\) 的子集个数,\(c_i\) 为 \(i\) 的出现次数,那么答案为:
\(S\) 容易 Möbius 反演求得,然后整一个 GCD 卷积就行了 .
过程需要用 Dirichlet 前缀和优化,时间复杂度 \(O(v\log\log v)\),其中 \(v\) 是值域 . 可以通过 .
这个也能用容斥推,最后得到的复杂度是一样的 .
3500
原题:CF1148H Holy Diver . 什么 CSP 模拟赛放 CF *3500 啊?
扫描线,考虑对于固定右端点维护所有左端点的 mex,注意到 mex 关于左端点显然单调不增,对于在末尾插入数 \(w\),只会更新 mex 等于 \(w\) 的位置,那么找到 mex 等于 \(w\) 的段 \([l,r]\) 之后,不断找到最小的满足最后一次出现位置 \(\operatorname{pos}(v)<r\) 的 \(v\),然后更新 \((\operatorname{pos}(v),r]\) 的 mex 即可完成过程 . 基于颜色段均摊的分析,可以得到修改的总段数是 \(O(n)\) 的 .
对于询问,对每个 mex 分别考虑,放在时间 - 下标二维平面上,一种 mex 的贡献可以看成若干个不交矩形之并,查询即为矩形求和,主席树维护即可 .
时间复杂度 \(O((n+q)\log n)\),可以通过 .
CSP 模拟 19
十年之约
考虑算满足 \(f(x)=k\) 的 \(x\) 的数量 \(c(k)\),显然要满足 \(1\dots k-1\) 都是 \(x\) 的因子,且 \(k\) 不是 \(x\) 的因子,那么朴素容斥即可得到:
动态维护当前的 \(\operatorname{lcm}(1,2,\cdots,k)\) 计算即可,注意到有贡献的 \(k=O(\log n)\),那么时间复杂度为 \(O(\log n)\),可以通过 .
可爱三小只
原题:CF446B DZY Loves Modification .
对于行列分别考虑,注意到如果行列交叉一次那么得到的权值减 \(p\),所以贪心处理出选 \(x\) 行 / 列得到的最大权值,枚举选多少行然后算就行了 .
时间复杂度 \(O(nm+n\log n+m\log m+k)\),可以通过 .
蛋糕塌了
原题:CF1316F Battalion Strength .
首先将原序列排序,那么对于一个序列,两个数 \(p_i,p_j\) 要产生贡献那么中间就不能有别的数,则概率为 \(\dfrac 1{2^{j-i+1}}\),那么答案就是:
这个信息实际上是可以合并的,具体类似最大子段和,首先继承左右的答案,然后考虑跨越中点的可以从中点拆开变成前缀和后缀的贡献 . 那么先离散化然后权值线段树维护即可 .
时间复杂度 \(O((n+q)\log n)\),可以通过 .
西安行
套路地考虑组合意义,问题变为有 \(n\) 个格子,放若干个隔板,有 \(m\) 个位置不能放隔板,相邻隔板间必须有恰好一个黑球一个白球(可以重合)的方案数 .
那么朴素 DP 即可,令 \(dp_{i,j}\) 表示考虑 \(1\dots i\) 且 \(i\) 到上一个隔板间放了 \(j\) 个球的方案数,那么不能放隔板的位置和能放隔板的位置的转移可以表为 DP 向量乘上一个矩阵,分 \(m\) 段分别矩阵快速幂即可 .
时间复杂度 \(\Theta(m\log n)\),可以通过 .
CSP 模拟 20
跳火山
不难发现 \([l,r]\) 中存在 \(d\) 的倍数当且仅当 \(\lfloor\frac rd\rfloor\cdot d\ge l\),那么也就是 \(\lfloor\frac rd\rfloor\ge\lceil\frac ld\rceil\) .
从而对于 \([a,b],\ [c,d]\) 存在一对数的 GCD 是 \(k\) 的倍数当且仅当 \(\lfloor\tfrac bk\rfloor\ge\lceil\tfrac ak\rceil\) 且 \(\lfloor\tfrac ck\rfloor\ge\lceil\tfrac dk\rceil\) .
对于 \(k\) 来说,二元组 \((\lfloor\tfrac bk\rfloor,\lfloor\tfrac dk\rfloor)\) 只有 \(\Theta(\sqrt{b+d})\) 种取值,整除分块处理后判断是否满足不等式即可,时间复杂度 \(\Theta(\sqrt{b+d})\),可以通过 .
赞美太阳
原题:POI2010 CHO-Hamsters .
令 \(dp_{i,j}\) 表示总共出现了 \(i\) 次,目前最后一个字符串是 \(j\) 的最短长度,那么只需要处理 \(d_{i,j}\) 表示 \(S_i\) 后面最少添加多少个字符使得字符串含 \(S_j\),那么转移可以写作 \((\min,+)\) 矩阵乘法,矩阵快速幂优化即可做到 \(\Theta(n^3\log m)\) .
\(d\) 是 border 状物,Hash 或者 KMP 即可预处理,总时间复杂度为 \(O(n\sum|S_i|+n^3\log m)\),可以通过 .
幽邃主教群
原题:JOISC2016 雇用計画 / 洛谷 P3616 富金森林公园 .
将序列看成一条链,应用 Trick 树上点边容斥变为维护点数和边数,然而这些都是好维护的,在值域上考虑就变为单点加区间求和,离散化后树状数组维护即可 .
时间复杂度 \(\Theta((n+q)\log(n+q))\),可以通过 .
整理
原题:ABC134F Permutation Oddness .
首先拆开绝对值,只关心每个位置对答案的贡献是正的还是负的,那么问题变成 \(\{1,1,2,2,\cdots,n,n\}\) 这个序列中给每个元素染黑色或白色,要求:
- 黑色元素权值和减白色元素权值和等于 \(k\) .
- 对于任意前缀黑色数量不小于白色数量 .
那么考虑给每个白色位置匹配一个黑色位置,需要记录目前染到的位置,奇数位和偶数位的黑色数量和当前的权值和之差,这样就得到了一个 \(\Theta(n^5)\) 的 DP .
注意到奇数位和偶数位的黑色数量几乎是同时增加的,那么考虑记录奇数位和偶数位黑色数量之差 \(d\),它只有三种取值:\(d=-1,0,1\),从而即可省去一维状态,时间复杂度 \(\Theta(n^4)\),可以通过 .
CSP 模拟 21
Get
原题:CEOI2016 kangaroo .
朴素排列 DP,令 \(dp_{i,j}\) 表示放 \(1\dots i\),放好了 \(j\) 个连续位置的方案数,那么考虑每次只有三种可能:
- 新增一个连续段 .
- 合并两个连续段 .
- 在连续段的一侧加一个元素(只有开头、结尾可能).
那么如上写出转移即可,时间复杂度 \(\Theta(n^2)\),可以通过 .
On
原题:JOI 2023 Final Advertisement 2 .
不难发现将每个居民的 \(X_i,E_i\) 看成二维平面上的一个点 \((X_i,E_i)\),那么满足 \(|X_i-x|\le E_i-y\) 的 \((x,y)\) 在二维平面上表现为 \((X_i,E_i)\)「右侧」的直角三角形 . 形式化的,半平面 \(y-x\le E_i+X_i\) 和半平面 \(x+y\le E_i+X_i\) 的交 .
那么连完边后图是一个 DAG,不难发现答案就是入度为 0 的点的个数,根据以上结论,对于点 \((i,j)\),有边 \(i\to j\) 当且仅当 \((X_j,E_j)\) 在 \((X_i,E_i)\) 右侧的直角三角形内,也就是 \((X_i,E_i)\) 在 \((X_j,E_j)\) 左侧的直角三角形内。从而问题变成计数某点左侧直角三角形点的个数 .
可以将「左侧的直角三角形」看成一侧的曼哈顿距离,那么使用变换:曼哈顿距离转切比雪夫距离 \((x,y)\to(x+y,x-y)\),这样的区域就变成一个矩形,问题也即变为二维数点。这是我们熟悉的问题,扫描线即可解决 .
时间复杂度 \(O(n\log n)\),可以通过 .
Your
(几乎)原题:THUPC2019 鸽鸽的分割 .
第一问显然是 \(\binom n4\),不表 .
关于第二问,考虑应用题目给出的欧拉公式 \(V-E+F=2\),那么 \(V=n+\binom n4\),\(E=n+\binom n2+2\binom n4\),从而 \(F=2+\binom n2+\binom n4\) .
那么时间复杂度为 \(\Theta(1)\),可以通过 .
也可以跑前几项暴力高斯消元 / 插值 .
Way
原题:ARC141F Well-defined Abbreviation .
注意到如果两个字符串 \(S_1,S_2\) 满足 \(S_1\subseteq S_2\),那么从 \(S_2\) 中删去 \(S_1\) 不会影响答案,如果删除过程中有字符串没有没删完,那么这个字符串本身就是对应多种删法的,可以直接输出 Yes
.
按上述流程删完之后,令剩下的字符串集合为 \(S\) .
断言:\(S\) 的方案不唯一当且仅当存在 \(A,B,C\) 满足 \(A\neq C\) 且 \(A+B,\,B+C\) 都在 \(S\) 中 .
证明:
首先令 \(f(S)\) 表示 \(S\) 能得到的字符串产生的集合 . 令 \(S_i=A+B,\,S_j=B+C\) .
-
充分性:下面证明如果不存在满足条件的 \(A,B,C\) 那么对于所有的字符串 \(T\) 有 \(|f(T)|=1\) .
考虑对 \(|T|\) 归纳,如果比 \(T\) 短的所有字符串 \(T'\) 都满足 \(|f(T')|=1\),那么考察 \(T_1=T\setminus\{S_i\},\,T_2=T\setminus\{S_j\}\),只需要证明 \(f(T_1)=f(T_2)\) .如果 \(T_1,T_2\) 有重叠,那么显然 \(T_1=T_2\) . 否则可以发现 \(f(T_1)=f(S\setminus\{S_i,S_j\})=f(T_2)\),得证 .
-
必要性:如果存在 \(s\in S_k\) 其中 \(k\neq i,j\) 且使得 \(A,C\) 中的一个包含 \(s\),那么肯定 \(S_i,\,S_j\) 包含 \(S_k\),这是和假设矛盾的 .
从而一定不存在一个 \(S_k\) 使得 \(A,C\) 包含 \(S_k\),那么对于 \(A+B+C\),它存在两种删法,分别得到 \(A\) 和 \(C\) .
证毕 .
那么考虑实现方面,问题分为两部分:
- 求 \(S\) .
- 判断是否存在满足条件的 \(A,B,C\) .
对于第一部分,考虑建立 AC 自动机,从小到大加入每个字符串,对于每个结点 \(u\),维护其 fail 树上最浅的是一个字符串的结尾的结点 \(\operatorname{submark}(u)\),然后每次删除 \(\operatorname{submark}(u)\) 这个后缀即可 .
对于第二部分,首先考虑对于一个字符串的后缀 \(B\),是否存在唯一的字符串 \(A\) 满足 \(C\subseteq A\),反之亦然 . 注意到后缀可以用 fail 树刻画,前缀可以用 Trie 树刻画,那么直接暴跳就行了 . 然后就是枚举 \(B\),Hash 判断两边是否相等了 .
时间复杂度 \(O(|\Sigma|\sum|S_i|)\),可以通过 .
CSP 模拟 22
骨架
考虑在边上统计贡献,相当于每条边选一个端点使得点权和最小 . 如果选择方案无环那么就能构造方案,然而点权的小于关系是偏序必然无环,所以只需要输出每条边端点点权最小值之和 .
时间复杂度 \(\Theta(n+m)\),可以通过 .
灌伤
原题:CF1598F RBS .
套路地把左括号换成 \(1\),右括号换成 \(-1\),那么一种括号串合法当且仅当和为 \(0\) 且前缀和任意时刻不小于 \(0\) .
考虑状压 DP,令 \(dp_S\) 表示选中集合 \(S\) 括号串后,最长的合法前缀 . 注意到后面接一个字符串是否还合法只和后面的前缀和加上目前的全局和有关,那么只需要记录当前的全局和 \(\operatorname{sum}(S)\) 和某个字符串的前缀最小值 . 如果某处最小值等于前缀最小值等于 \(k\),那么它就可以被直接接在一个和为 \(-k\) 的序列后面,由此转移即可 .
时间复杂度 \(\Theta(n2^n)\),可以通过 .
虚化
升级成功后肯定是一直选 \(b\times p\) 最大的游戏玩,那么只需要考虑升级前的决策 .
令 \(dp_t\) 为剩 \(t\) 秒且未升级的最大期望收益,最大的 \(b\times p\) 为 \(v\),则:
改成斜率优化形式:
注意到斜率是单调的,所以可以单调队列维护,时间复杂度 \(\Theta(n+t)\),然而过不了 .
不过可以发现凸包上事实上只有 \(O(n)\) 个点,每个斜率一样的段的转移是一样的,可以矩阵乘法优化,具体的:
那么倍增计算即可做到 \(O(n\log t)\),可以通过 .
闪光
原题:USACO18JAN Cow at Large P .
首先可以发现如果令 \(l_i\) 为 \(i\) 到最近的叶子间的距离如果一个点 \(u\) 满足 \(\operatorname{dep}(u)\ge g_u\) 且 \(\operatorname{dep}(\operatorname{fa}(u))<g_{\operatorname{fa}(u)}\) 那么 \(u\) 就需要一个农民 .
所以问题就是对于每个根算上面的答案,考虑对于一棵 \(n\) 个点的子树有 \(\sum\deg(u)=2n-1\),也就是 \(\sum(2-\deg(u))=1\),所以只需要计算满足条件的点的所有子树内的点的 \(2-\deg(u)\) 之和即可,也就是算:
点对统计问题,点分治处理即可,时间复杂度 \(O(n\log^2n)\) 或 \(O(n\log n)\),可以通过 .
CSP 模拟 23
电压
原题:JOISC2014 电压 / 电压机制(这里面代码有点问题) .
题意即为有多少条边使得删去后图为二分图且这条边的端点在同一部,即求所有奇环并的大小 .
先搜出一棵 DFS 数,特判只有一个奇环的情况,然后对于每条返祖边树上差分即可 . 因为注意到对于任意一个环,可以有若干个只有一条非树边的环异或组成,证明类似最大 XOR 和路径,所以上述过程是正确的 .
时间复杂度 \(\Theta(n+m)\),可以通过 .
农民
原题:LOJ #6498 农民 .
考虑进入一个左儿子相当于对最终位置的权值增加一个上界限制,反之则为下界限制 . 于是考虑维护每个左儿子父亲的权值 min/max 和所有右儿子父亲的权值 min/max,单点修改可以简单维护,子树翻转相当于交换左右儿子信息,对于链查询树剖维护即可,时间复杂度 \(O(n\log^2n)\),可以通过 ,
奇迹树
原题:ARC117D Miracle Tree .
将点权从小到大排序,让标号排列为 \(\{p\}\),则只需要满足相邻的项的距离限制,也就是 \(E_{p_{i+1}}-E_{p_i}\le\operatorname{dist}(p_i,p_{i+1})\),别的位置可以用三角形不等式调整得到满足限制 .
关于限制,显然全部取等是可以的,于是可以导出的是 \(\displaystyle E_{p_k}=1+\sum_{i=1}^{k-1}\operatorname{dist}(p_i,p_{i+1})\) .
那么问题就变成了找到排列 \(\{p\}\) 使得 \(\displaystyle\sum_{i=1}^{n-1}\operatorname{dist}(p_i,p_{i+1})\) 最小了,看起来比较经典 .
首先加上 \(\operatorname{dist}(p_n,p_1)\) 之后按 DFS 序选就可以取到下界 \(2(n-1)\),那么只需要最大化 \(\operatorname{dist}(p_n,p_1)\),取直径端点即可 .
时间复杂度 \(\Theta(n)\),可以通过 .
暴雨
因为一个积水区域的下边界肯定是单峰的,所以考虑枚举最大值位置,然后只需要限制左右的高度(为了避免算重最大值重复的情况只能有一个方向取等),做一个前后缀的 DP 然后合并就行了 .
具体地,不妨考虑前缀,令 \(dp_{i,j,l,c=0/1}\) 表示考虑 \(1\dots i\),最大值为 \(j\),推平 \(l\) 个位置,目前积水体积和模 \(2\) 等于 \(c\) 的方案数 . \(j\) 只有 \(O(k)\) 种,可以预先离散化处理 . 转移略,合并也没有什么难点 .
沈老师说可以直接记偶数减奇数的,这样也可以一样转移,膜拜 .
时间复杂度 \(\Theta(nk^2+n\log n)\),可以通过 .
CSP 模拟 23
原神派蒙
原题:THUPC2022 初赛 造计算机 .
对每个置换环分别考虑,就拿一个寄存器把第一位处理了,另外一个做循环移位,然后交错着交换就好了 .
时间复杂度和操作次数 \(\Theta(n)\),使用寄存器个数 \(m=2\),可以通过 .
药水泡面
根据期望线性性,考虑算出每个结点被选中的概率之和,也就是其子树内第一个选择的是自己的概率之和,那么就是 \(\displaystyle\sum_u\dfrac1{\operatorname{size}(u)}\),直接计算即可 .
时间复杂度 \(\Theta(n)\),可以通过 .
医生拍门
原题:AGC023E Inversions .
在 \(\{a\}\) 中从小到大排依次选可以知道合法排列个数:
记 \(c_k=\sum_{i=1}^n[a_i\ge k]-(n-k)\) .
对每个 \(i<j\) 计算 \(p_i>p_j\) 的排列个数,不妨令 \(a_i\le a_j\),\(a_i>a_j\) 时单步容斥即转为类似情况 .
先考虑 \(p_i,p_j\) 的取法,然后别的随便选,对于 \((a_i,a_j]\) 内的数选法减一 . 那么可以写出答案:
类似二维偏序的统计 . 转为前缀积后,依次加入 \(a_{1\dots}\),用树状数动态维护对应的前缀和即可 .
对于 \(c_k=1\) 情况需要特殊处理,具体可以记上一个的 \(c_k=1\) 的位置 .
时间复杂度 \(\Theta(n\log n)\),可以通过 .
浴室泡沫
原题:AGC061C First Come First Serve .
注意到如果选一个 \(b_i\) 能改变最终的顺序那么必须有人选 \((a_i,b_i)\) 内的数 . 考虑容斥,钦定一簇区间 \((a_i,b_i)\) 中都不被选,那么这要求所有与 \((a_i,b_i)\) 有交的区间 \([L_k,R_k]\)(这些区间的编号肯定是连续的)必须选远离 \((a_i,b_i)\) 的一侧,那么可以得到方案的贡献为:
需要计算每种局面的贡献和,考虑 DP . 令 \(dp_i\) 表示完全包含 \(1\dots i\) 的局面的权值和,那么可以转移:
前缀和优化即可做到 \(\Theta(n)\),可以通过 .
CSP 模拟赛 25
考前欢乐赛 .
炒币
取 log DP 即可 .
时间复杂度 \(\Theta(n)\),可以通过 .
凑数
原题:ARC139B Make N .
钦定 \(y<ax\),\(z<bx\),否则可以用 \(1\) 操作代替,然后让 \(\dfrac ya\le\dfrac zb\),否则可以交换 .
于是步长为 \(a\) 的操作最多 \(\left\lfloor\dfrac na\right\rfloor\) 次,\(b\) 操作最多 \(a-1\) 次 .
注意到 \(\min\left\{\left\lfloor\dfrac na\right\rfloor,a-1\right\}\le\sqrt n\),于是俩暴力拼一起即可,时间复杂度 \(\Theta(T\sqrt n)\),可以通过 .
同构
原题:CF698F Coprime Permutation 弱化版 .
考虑对标准排列作一些交换得到 .
按 \(\displaystyle f(n)=\prod_{\substack{p\mid n\cr p\text{ is prime}}}p\) 分成若干类,则类间显然可以随便排,阶乘乘起来即可 .
然后 SoyTony 给出一种情况:5 7 10 14 -> 7 5 14 10
,原因是除了这些数以外没有数与其有公因子,而其内部整体改变位置也是合法的 .
形式化的就是 \(\left\lfloor\dfrac na\right\rfloor=\left\lfloor\dfrac nb\right\rfloor\) 且 \(a,b\) 为素数的时候就可以换,整除分块一下即可 .
时间复杂度单次 \(\Theta(n)\),可以通过 .
最近公共祖先
先考虑先修改再询问的 case,那么就是简单 DP:
那么对于一般情况考虑每次修改的时候更新 DP 数组,只需要暴力跳祖先转为 DFS 序区间修改就可以了,这个可以线段树维护 .
注意到每个结点不会由黑色变为白色,对于一次更新,当前结点如果被更新过了就不更新了直接跳出,那么均摊下来复杂度就对了 . 时间复杂度 \(\Theta((n+q)\log n)\),可以通过 .
CSP 模拟 26
Reversi
原题:AGC031B Reversi .
对于每个颜色考虑可以发现操作不交也可以得到所有可能最终局面于是线性 DP 即可 .
时间复杂度 \(\Theta(n)\),可以通过 .
Non-Decreasing Dilemma
原题:CF1567E Non-Decreasing Dilemma .
线段树维护当前答案、左边最长段长度、右边最长段长度、左边数值、右边数值和区间长度即可 .
时间复杂度 \(\Theta((n+q)\log n)\),可以通过 .
Synchronized Subsequence
原题:AGC026E Synchronized Subsequence .
一对一对考虑,注意到比较两个字符串的字典序时,当某个前缀相同时应该比较后缀,所以从后往前 DP .
令 \(dp_i\) 表示 \(i\dots n\) 对形成的最大串,\(a_i,b_i\) 表示第 \(i\) 对 \(\tt a,b\) 的位置 .
讨论:
- \(a_i<b_i\),那么保留 \([a_i,b_i]\) 内的元素肯定有至少一个 \(\tt a\),这是不优的,所以需要把中间的全删了,并删掉与其配对的对 .
- \(a_i>b_i\),这时候要处理尽量多的 \(\tt b\),首先保留 \([b_i,a_i]\) 间的 \(\tt b\),这造成的结果就是后面会有一些 \(\tt a\) 被选中,同样需要加入这些 \(\tt a\) 对应的 \(\tt b\),重复过程直到停止即可 .
那么模拟以上过程即可做到 \(O(n^2)\),可以通过 .
Star MST
原题:CF1657E Star MST .
首先不难得到答案的表达式:
为了去掉 max 的限制,从小到大加入 \(w\) DP 即可 .
时间复杂度 \(\Theta(n^2k)\),可以通过 .
CSP 模拟 27
道路
原题:CF1060E Sergey and Subway .
答案即为所有路径长度除以二向上取整的和,算出所有路径长度加上长度为奇数的路径数然后除以二即可 .
长度为奇数的路径数可以考虑两端点的深度奇偶性必然不相同,即可简单统计 .
时间复杂度 \(\Theta(n)\),可以通过 .
集合
原题:CF979D Kuro and GCD and XOR and SUM .
首先因为 \(k\mid\gcd(v,x)\iff k\mid v\land k\mid x\),所以判完 \(k\mid x\) 后就是限制 \(k\mid v\) .
考虑阈值分治,对于 \(k\le B\),给每个 \(k\) 开一棵 0-1 Trie 存储所有 \(k\) 的倍数,那么问题就是 0-1 Trie 上查询带上界的最大异或和 . 每个结点维护子树内表示的数的最小值,查询时贪心查找,只查找最小值 \(\le s-x\) 的位置即可保证不超上界 .
对于 \(k\ge B\),每次加入时用一个 set 记录,查询时暴力查询所有 \(k\) 的倍数即可 .
取 \(B=90\),可以通过。
科目五
原题:CF1101F Trucks and Cities .
对于每个行程分别处理,那么问题就是划分为 \(r+1\) 段,使得最大值最小 .
考虑区间 DP,令 \(dp_{l,r,k}\) 表示 \([l,r]\) 中划分为 \(k\) 段的答案,那么有:
注意到 \(dp_{l,i,k-1}\) 单调增,\(a_r-a_i\) 单调减,所以右式单峰,使用双指针优化即可 .
时间复杂度 \(\Theta(n^3)\),可以通过 .
监狱
原题:JOISC2022 监狱 .
考虑如果一条路径的开头与某条别的路径相交,那么这条路径必须先走,结尾类似,那么可以建立出若干点的先后顺序关系,这个可以树剖线段树优化建图或倍增优化建图处理,然后问题相当于判断图是否有环,拓扑排序即可 .
时间复杂度 \(O(n\log^2n)\) 或 \(O(n\log n)\),可以通过 .
CSP 模拟 28
k
原题:CF1681E Labyrinth Adventures .
走的过程分为从起点到门、从门到门、从终点到门三部分 .
只有第二部分是非平凡的,可以设计朴素 DP 然后用矩阵描述,这样问题即为区间求积,咋做都行了 .
时间复杂度 \(O((n+q)\log n)\),可以通过 .
kk
原题:BJOI2019 光线 .
考虑合并两块玻璃,令 \(p,q\) 表示透光率和反射率,则对于两块玻璃 \((p_0,q_0),(p_1,q_1)\),合并后就是:
模拟上述过程即可,不算求逆元时间复杂度 \(\Theta(n)\),可以通过 .
kkk
对序列 \(\{x\}\) 排序后一个前缀 max \(\{s\}\) 合法当且仅当 \(\{s\}\) 仅包含 \(\{x\}\) 中的数且对于任意 \(i\) 有 \(s_i\ge x_i\) .
那么考虑 DP,令 \(dp_{i,j}\) 表示长度为 \(i\) 的 \(s_i=j\) 的 \(\{s\}\) 个数,转移比较朴素,前缀和优化即可做到 \(\Theta(n^2)\) .
kkkk
首先根据简单容斥,令 \(f(i)\) 表示钦定 \(i\) 个位置 \(|p_i-i|=k\) 的方案数,则答案就是:
那么就是要求选这些位置的方案数,然后乘上别的地方随便选的方案数 \((n-i)!\) 即可 .
那么考虑给每个位置 \(i\) 建立两个点 \(u_i,v_i\),选择 \(u_i\) 表示 \(a_i=i+k\),选择 \(v_i\) 表示 \(a_i=i-k\) .
那么连若干限制边后变成求一些链并的大小为 \(i\) 的独立集个数,对于每条链分别做然后卷起来即可,时间复杂度 \(\Theta(n^2)\),可以通过 .
注意到链只有两种本质不同的长度,那么也就是对于两个 OGF \(F,G\),要求 \([z^k]F(z)^{k_1}G(z)^{k_2}\),使用多项式基本操作即可 \(O(n\log n)\) . 注意到这里 \(F,G\) 只有 \(O(n)\) 项,也可以直接对有值的部分 DFT 然后点值快速幂后 IDFT 回去 .
CSP 模拟 29
树篱之途
注意到对于两棵子树,合并后重心一定在两子树重心的连线上上,那么每次暴力跳,如果跳到重心就直接返回即可 . 关于判断重心,如果割掉点 \(u\) 后每个连通块大小都 \(\le\lfloor\frac n2\rfloor\) 那么 \(u\) 是重心 .
均摊下来每个点只会被遍历 \(\Theta(1)\) 次,时间复杂度 \(\Theta(n)\),可以通过 .
坍缩
原题:CF1080E Sonya and Matrix Beauty .
一个矩阵合法当且仅当:
- 每行都可以重排为回文串 .
- 整个矩阵的每行看做集合,那么矩阵关于列回文 .
第一个条件好做,第二个条件相当于出现次数数字回文,对出现次数数字 Hash 后 Manacher 即可 .
时间复杂度 \(\Theta(n^3)\),可以通过 .
诡意行商
原题:CF1023F Mobile Phone Network .
经典题,首先把 \(k\) 条边钦定入 MST 中,别的边正常 Kruskal 加入 . 后面对于每条非树边到 MST 上 checkmin 即可 .
有一个比较快的做法,可以做到 \(\Theta(n+q)\),可以通过 .
越过群山
原题:JOISC 2022 京都观光 .
考虑行 \(x<y<z\),列 \(l<r\),那么从 \((x,l)\) 到 \((y,r)\) 有三条路径:
- \((x,l)\to(x,r)\to(z,r)\):代价 \((r-l)a_x+(z-x)b_r\) .
- \((x,l)\to(z,l)\to(z,r)\):代价 \((r-l)a_z+(z-x)b_l\) .
- \((x,l)\to(y,l)\to(y,z)\to(z,r)\):代价 \((r-l)a_y+(y-x)b_l+(z-y)b_r\) .
经过 \(y\) 较优当且仅当最后一个式子比前面小,整理得:
中间的项没啥用,这指出最优决策点必然在 \(a\) 的下凸壳上,同理可以得到最优决策点也必然在 \(b\) 的下凸壳上 .
对于合并信息,类似 Minkowski 和,每次贪心选一个方向走就可以了 .
时间复杂度 \(\Theta(n)\),可以通过 .
CSP 模拟 30
枫
原题:洛谷 P7485 「Stoi2031」枫 .
考虑递归处理,一轮删除后问题变为规模为 \(n-\lceil\frac nk\rceil\) 的子问题,如果子问题的答案为 \(p'\),那么整体的答案即为 \(p'+\lceil\frac{p'}{k-1}\rceil\),递推做就好了 .
时间复杂度 \(\Theta(nk+\sum q)\),可以通过 .
Little Elephant and Broken Sorting
原题:CF258D Little Elephant and Broken Sorting .
首先根据期望线性性改为计算最终 \(p_i>p_j\) 的概率 .
令 \(e(i,j)=\mathbb P(p_i>p_j),\)那么考虑进行一次交换对 \(e\) 的影响即可 .
时间复杂度 \(\Theta(n(n+m))\),可以通过 .
楼房重建
原题:洛谷 P4198 楼房重建 .
线段树维护单调栈板子题 .
Yes or No
原题:AGC019F Yes or No .
不妨令 \(n\ge m\) .
肯定是哪个剩的多猜哪个优秀 . 看成网格图上从 \((0,0)\) 走到 \((m,n)\),往上走一步表示当前答案是 NO
,往右走一步表示当前答案是 YES
. 那么不在 \(y=x-n+m\) 上的部分肯定猜对恰 \(\max\{n,m\}\) 个,这个不难发现 . 那么只需要考虑 \(y=x-n+m\) 上的情况,只需要对于每个点 \((i,i-n+m)\) 统计贡献就行了,最终的式子是:
直接计算即可 \(\Theta(n+m)\),可以通过 .
要看详细题解找 joke3579:闲话 23.3.2 .
CSP 模拟 30++
工业题 / a
对于每个位置考虑贡献,可以发现一个位置递推到最终位置乘上的 \(a,b\) 数量是一定的,那么只需要计算路径数然后乘起来求和就好了 .
时间复杂度 \(\Theta(n+m)\),可以通过 .
卡常题 / b
对于每个 Y 方点 \(i\) 连接 X 方点 \(u,v\),相当于限制 \(u,v\) 中至少选一个 . 建立新图使得 \(u,v\) 有边当且仅当存在 Y 方点 \(i\) 使得原图有边 \((u,i),(v,i)\),那么建立出的图是连通的 \(n\) 个点 \(n\) 条边的无向图,即基环树,问题即为基环树上的最小权点覆盖 .
选一条环上的边 \((u,v)\) 断开以 \(u,v\) 分别为根 DP 然后合并即可 .
时间复杂度 \(\Theta(n)\),可以通过 .
玄学题 / c
注意到 \(d(x)\) 为奇数当且仅当 \(x\) 是完全平方数,而和的奇偶性只和求和项中奇数的个数有关,所以只需要计数 \(i\cdot j\) 中完全平方数的个数 .
枚举 \(i\),线性筛处理出最小的 \(d\) 使得 \(i\mid d^2\)(这个甚至是积性的),然后即可简单计算满足条件的 \(i\cdot j\) 的数量 .
时间复杂度 \(\Theta(n)\),可以通过 .
CSP 模拟 31
你相信引力吗
先把环复制一遍变成链,钦定在最大值处断开,那么可以朴素单调栈维护 .
时间复杂度 \(\Theta(n)\),可以通过 .
marshland
原题:洛谷 P4142 洞穴遇险 .
把没有危险的点黑白染色,使得每个 L 形都是从白点入、黑点出,这样直接连上即为网络流模型 . 需要在有危险的点设置流量限制保证 L 不重叠,同时设置费用 . 然后跑最小费用可行流即可 .
时间复杂度 \(\Theta(\operatorname{flow}(n^2,n^2))\),可以通过 .
party?
首先肯定是所有人到 LCA 集合,那么可以用 bitset 维护出每个人路径上有的颜色 .
那么可以建立二分图模型:左部点是 \(c\) 个人,每个人有 \(k\) 的流量 . 右部点 \(m\) 种特产 . 每个人向它路径上有的特产连边,那么问题就是满流的最大流 .
根据 Hall 定理,二分图存在完美匹配当且仅当对于任意 \(k\),左部任意 \(k\) 个点在右边的邻接点个数 \(\ge k\) .
因为 \(c\) 非常小直接 \(2^c\) 枚举即可,这样就可以了 .
时间复杂度 \(O(\frac m{\omega}(n+qc\log n+q2^c))\),可以通过 .
半夜
令 \(X\gets X+X\) 那么只需要对 \(X\) 的每个长度为 \(n\) 的子串和 \(Y\) 求 LCS 就行了 .
令 \(dp_{i,j,k}\) 表示 \(X[i:j],\,Y[1:k]\) 的 LCS,转移略 . 那么有以下两个性质:
感性理解的话就比如第一个的 \(dp_{i-1,j,k}>dp_{i-1,j-1,k}\) 意味着 \(X_j\) 可以和 \(Y\) 中的字符匹配,那么将 \(i\) 移动一位对 \(j\) 没有影响,并且对别的部分影响相同,所以一定有 \(dp_{i,j,k}>dp_{i,j-1,k}\),第二个类似 . 正经证明好像是考虑网格图游走 .
那么根据这两条性质,可以知道一定存在分界点 \(p(j,k),\,q(j,k)\) 使得:
那么只需要求出 \(p,q\) 就可以对于每一个 \(x\) 做 \(\Theta(n)\) 递推求出 \(dp_{x,x+n-1,n}\) .
对于 \(p,q\) 的求解,令 \(F=dp_{i,j-1,k-1},\,P=p(j,k-1),\,Q=q(j-1,k)\),分为三种情况讨论:
- \(X_j\neq Y_k\land P<Q\) .
- \(X_j\neq Y_k\land P\ge Q\) .
- \(X_j=Y_k\) .
每种分别列出表格来就可以看出转移了,这里以第一种情况为例:
这里表格的前两行是 \(P,Q\) 的定义,第三行由暴力 DP 得到,那么可以观察到 \(p(j,k)=Q,\,q(k,j)=P\) .
剩下两种情况就不一一写出了,那么时间复杂度为 \(\Theta(n^2)\),可以通过 .
完结了!撒花~
就以 yspm 的语录来结尾吧:
以下是博客签名,正文无关
本文来自博客园,作者:Jijidawang,转载请注明原文链接:https://www.cnblogs.com/CDOI-24374/p/17572380.html
版权声明:本作品采用「署名-非商业性使用-相同方式共享 4.0 国际」许可协议(CC BY-NC-SA 4.0)进行许可。看完如果觉得有用请点个赞吧 QwQ