杂题选做-6
#51 P11363
约定可以作为起始边的边为关键边。
考虑 \(k=1\) 怎么做。
考虑每一个点 \(u\),以它为端点的边中第一个被访问的边是确定的(离起始边最近的那一条),之后剩下的边就可以任意排序,于是记 \(i\) 号点度数为 \(d_i\)。于是答案就是 \(\prod(d_i-1)!\)。
考虑 \(k=2\) 怎么做。
首先,答案一定不是 \(2val\),因为会算重某些树。判断一个点周围的边的访问顺序是否合法,需要判断第一条被访问的边是否离起始边最近。考虑原图中不在 \(e_1\) 和 \(e_2\) 之间的边,它被访问到的第一条边一定既和 \(e_1\) 最近又和 \(e_2\) 最近,那么它对答案的贡献还是 \((d_i-1)!\);如果它在链上呢?那么它离 \(e_1\) 最近和离 \(e_2\) 最近的边就不是一条了,于是我们钦定这样的点第一条被访问的边离 \(e_1\) 最近,最后一条离 \(e_2\) 最近,那么贡献为 \((d_i-2)!\)。
考虑 \(O(nk)\) 的部分。
还是先考虑去重,然后考虑一颗树可以被三条及以上的边遍历出来需要满足什么条件。观察一个点合法的条件,发现此时条件能够被满足当且仅当这些边都在原树一条链上。然后可以考虑如下方法:记 \(f_i\) 表示选取钦定有 \(i\) 条边重复计数的树的个数。那么可以枚举两条关键边 \(e_i,e_j\),然后统计这两条边之间有多少关键边,记为 \(v\),那么有贡献:\(f_i \leftarrow f_i +\binom{v-2}{i-2}val\),其中减 \(2\) 是因为钦定左右两端必须为 \(e_i,e_j\),\(val\) 是以 \(e_i\) 和 \(e_j\) 为关键边时 \(k=2\) 的答案。
最后答案为 \(\sum_{i=1}^{k}(-1)^{i-1}f(i)\),精细实现可以做到 \(O(nk)\)。
对每一对关键边把对 \(f(i)\) 的贡献带入对答案的贡献观察是否有性质:\(\sum_{i=0}^{v-2}(-1)^i\binom{v-2}{i-2}val=val\times[v=0]\)。因此只有中间没有其他关键边的两条关键边对答案有有效贡献。
统计答案时考虑将所有关键边断开,然后在上面跑换根 dp:先钦定每一条点都贡献 \((d_i-1)!\),然后对每一条点维护从它出发到每一条关键边路径上需要去除的贡献之和。
时间复杂度为 \(O(n)\)。
#52 P11364
首先,做转化:区间 LCA 的深度为 \(\min \limits_{l \le i < r}dep_{LCA(i,i+1)}\)。
那么可以对每一个 \(i\) 预处理 \(dep_{LCA(i,i+1)}\) 做最小值的最大区间记为 \([x_i,y_i]\),然后定义三元组 \((x_i,y_i,v_i)\),其中 \(v_i=dep_{LCA(i,i+1)}\)。这里可以通过单调栈实现。
约定:下文提到的 \(k\) 和 \(r\) 均减去 \(1\),至于 \(k=1\) 询问,直接转化为 \(RMQ\) 问题即可。
那么询问就是找出与 \([l,r]\) 交集长度为 \(k\) 的区间中 \(v_i\) 的最大值。以此进行分类讨论:
-
交集在左侧:\(l+k-1 \le y_i \le r \and y_i-x_i+1 \ge k\);
-
交集在右侧:\(l\le x_i\le r-k+1 \and y_i-x_i+1 \ge k\);
-
贡献区间覆盖询问区间:\(l_i \le l \and r \le r_i\);
由二维偏序想到扫描线,做法是简单的。
#53 CF2060G
观察性质:操作等同于交换两列,然后再翻转这两列。
然后有一个想法:最终序列一定是按 \(\min(a_i,b_i)\) 排序得到的。证明可以通过反证法。
接下来我们需要继续观察性质。
因为上述排序的实现需要依靠题目中的操作,但是题目的操作包括翻转,所以考虑能否只交换两列,并且不翻转呢?可以,因为可以选择任意三列 \(a,b,c\)(需要交换 \(a,c\)),然后执行操作 \((a,b),(b,c),(a,b)\) 即可;
因为排序后不能保证对应序列是合法,可能需要翻转,所以考虑能否在不交换位置的情况下翻转两列?可以,在上述操作基础上,再操作 \((a,c)\) 即可。
那能不能翻转奇数列呢?不能,考虑任意一次操作都会修改两列的翻转情况,所以被翻转的列数变化量只可能是 \(-2,0,2\);故不能翻转奇数列。
性质足够了,开始 dp。定义 \(f_{i,j}\) 表示考虑前 \(i\) 个数,并且交换情况为 \(j(0 \le j \le 3)\)。其中 \(j\) 的第一个二进制为表示当前列是否交换,第二个二进制表示当前翻转次数的奇偶性。转移是简单的。
#54 CF1989E
首先,将 \(a\) 划分为若干极长同色连续段,然后将每一个连续段的长度记录下来,得到 \(c\)。那么 \(c\) 和 \(b\) 在大部分情况下一一对应。
发现对于一个不在 \(a\) 首尾的连续段,如果它的长度为 \(2\),那么它生成的 \(b\) 数组为 \([1,1]\),和两段长度为 \(1\) 的连续段生成的序列一样。所以钦定除首尾不能划分长度为 \(2\) 的连续段。
于是题意转化为将原序列转化为划分为至少 \(k\) 段的方案数, \(O(nk)\) 的带前缀和优化的朴素 dp 是简单的。值得一提的是,为了刻画长度不能为 \(2\) 的限制,需要在转移时减去当前状态对应的划分长度为 \(2\) 的状态。
#55 CF1930E
注意到可以枚举操作次数,因为操作次数总和为调和级数。因为一个数只有删了和没删两种状态,所以题目转化为合法 \(01\) 串计数(约定 \(0\) 是没有被删的)。
然后考虑一个合法的序列需要满足什么条件:存在一个零左右有至少 \(k\) 个 \(1\)。显然,不然最后一次操作就没有办法做了。那这是否是充分呢?是的,因为总可以构造方案使得上一次操作的第 \(k+1\) 个数被删掉,于是只剩最后一次操作不能这么做,因此只判断其合法性即可。
但是,“至少”类计数大多不太好求,于是容斥转化为求非法数量。考虑枚举操作次数 \(x\),那么 \(1\) 的总数为 \(m=2xk\),总方案数为 \(\binom{n}{m}\);观察非法方案,发现其中都有一个长度为 \(m-2k+2\) 的连续 \(1\) 段,然后其左右两边各有 \(k-1\) 个 \(1\)。那么将这 \(m-2k+2\) 个 \(1\) 视为一个点,非法方案数就是 \(\binom{n-m+2k-1}{2k-1}\)。
#56 ABC421G
看到递增或递减可以尝试考虑差分。
差分后限制转化为差分数组 \(a\) 每一项都大于等于 \(0\)。一次操作相当于 \(a_l\) 加一,\(a_{r+1}\) 减一。
然后观察数据范围,\(n,m,a_i \le 300\)。然后考虑网络流:
-
对小于 \(0\) 的元素 \(a_i\),连边 \(i \rightarrow T\),容量为 \(-a_i\),费用为 \(0\)。
-
对大于 \(0\) 的元素 \(a_i\),连边 \(S \rightarrow i\),容量为 \(a_i\),费用为 \(0\)。
-
对每一个操作,连边 \(r+1 \rightarrow l\),容量 \(+\infty\),费用为 \(1\)。
特别地,可以将 \(a_{n+1}\) 视为 \(-\infty\)。
#57 CF1842F
如果我们已知每一个节点子树内的黑点个数 \(sz_i\),那么其对答案贡献就是 \(|k-2sz_i|\)。绝对值形式的贡献一般只有两个方向:一是转化,二是拆。优先考虑后者。考虑能否使上述贡献始终为正:即需要 \(sz_i\) 最小,因此考虑在黑点重心处进行答案统计。
依据重心的性质,此时贡献一定为正,那么答案就是 \(\sum_ik-2sz_i\)。考虑每一个黑点对答案的贡献,就是其深度。于是问题转化为使所有黑点深度最小,贪心地从小往大选即可。由于不在重心上时,这么拆绝对值贡献只可能变小,因此这么做是正确的。
时间复杂度为 \(O(n^2)\) 或 \(O(n^2\log n)\)。
#58 P14364
首先,定义 \(k=\sum_{i=1}^ns_i,w_i=\sum_{j=1}^{i-1}s_j\) 。因为只有这 \(k\) 个人是可能被雇用的,所以只需讨论他们是否被雇用即可。
考虑一个人什么时候会走。若它的忍耐值为 \(v_i\)(即原序列中的某个 \(c_i\)),在 \(i\) 之前走了 \(t_i\) 个人,那么如果有 \(v_i \le w_i+t_i\),那么这个人会跑。限制类似偏序关系,所以给 \(c\) 按升序排序。
考虑一个走(或不走)会对之后造成什么影响。如果它没走,即要求 \(v_i >w_i+t_i\);走了,就要求 \(v_i \le w_i+t_i\)。
两个方向都有限制,难以刻画限制。怎么呢?还是容斥。我们钦定其一定不合法,也就是钦定 \(v_i \le w_i+t_i\),容斥系数乘 \(-1\);另一部分也就是当前位置的总选择情况,现在变成 \(v_i \in R\) 了,直接和那些必定选不到的人一起处理即可。这被成为反向容斥。
至此,状态设计是简单的,设 \(f_{i,j,k}\) 表示已经考虑了前 \(i\) 个人,并且反向容斥了没有走的 \(j\) 个人,没有走的人中有 \(k\) 个容斥了。
转移和答案统计都容易,只是注意统计答案时要统计那些不在状态内的人的贡献,即不可能雇用的人和没有容斥的人,也就是说统计答案是要乘 \((n-x-y)!\) 的系数。
#59 P14568
感谢出题人给的每一档部分分。
首先,题目限制既有前缀又有后缀,这不太好做,于是考虑能否将后缀的限制转化为对前缀的限制。
假设当前已经考虑到 \(i\) 位置,已用的数字集合为 \(S\),那么对应的后缀中出现的数集为 \(S\) 的补集。如果此时要满足第三种限制,那么 \(a_i\) 要小于后缀中的每一个数,所以 \(a_i\) 必须选 \(S\) 补集中的最小值;第四种限制同理。
接下来可以通过指数级暴力算法对特殊性质进行分析,发现当在特殊性质 B 中(\(op_i \in \{0,2\}\)) 时,答案不为零,当且仅当所有满足 \(op_i=0\) 的位置是 \(op\) 的一个前缀,满足 \(op_i=2\) 的位置是 \(op\) 的一个后缀。稍加分析,其实是显然的:如果在 \(op\) 序列中有 \(op_i=2,op_j=0(i<j)\),那么 \(a_i\) 就是后缀最大值,\(a_j\) 不可能大于 \(a_i\),所以无合法方案。对于 \(opt_i \in \{1,3\}\) 是类似的。
注意到特殊性质 C 出现了两次,想必是关键性质,于是先来分析它。观察发现限制一只和前缀最小值相关,限制四的取数方案唯一。因此定义 \(f_{i,j}\) 表示已经考虑了前 \(i\) 个数且前缀最小值为 \(j\) 的方案数。转移不难:
最后一个转移是因为此时大于等于前缀最小值的数都已经出现过了,只能选择比前缀最小值小的数。第一个转移可以前缀和优化。时间复杂度为 \(O(n^2)\)。
接下来继续观察特殊性质:注意到在特殊性质 A 中(\(op_i \in \{0,1\}\)),答案恒为 \(1\)。尝试证明:将 \(op_i=1\) 和 \(op_i=0\) 的位置分别抽出来,会发现前者是一段递增序列,后者是一段递减序列,它们总长度为 \(n\),与值域相同,所以存在唯一解。
注意到上述观察可以推广到一般情况,那么其实可以把 \(op\) 序列分成三段:第一段满足 \(op_i \in \{0,1\}\),第二段满足 \(op_i \in \{1,2\}\) 或 \(op_i \in \{0,3\}\),第三段满足 \(op_i \in \{2,3\}\)。
第二段其实就是特殊性质 C,另一种情况稍微改一下就可以了,直接做即可。
第一段类似特殊性质 A,考虑类似证明一样计数。具体地,定义 \(g_{i,j}\) 表示序列长度为 \(i\) 且最后一个元素和第一个元素的差为 \(j\) 的合法方案数和 \(h_{i,j}\) 表示序列长度为 \(i\) 且最后一个元素和第一个元素的差至少为 \(j\) 的合法方案数。转移就是 \(g_{i,j}=\sum \limits_{l=1}^{n-i-j+2}g_{i-1,j-l}\),\(h\) 就是对 \(g\) 做一次前缀和。计数时,先统计前缀中 \(1\) 和 \(0\) 的个数,然后方案数就是对应的上升序列和下降序列的方案数的乘积(Tip:这里不能统计 \(op_1\),想想为什么)。
第三段就完全是特殊性质 A。所以可以忽略。
总时间复杂度为 \(O(n^2)\)。
#60 CF2002E
考虑如果没有合并,那么就是最大值。
那么什么情况下会有合并?当且仅当两个同色段之间的异色段被消完了。这启发用单调栈解题。
具体地,维护递减的单调栈,遇到栈顶和即将插入的元素同色时,就将已弹出的最大的异色栈顶的数量减去,然后合并二者进行判断能否弹出栈顶。

浙公网安备 33010602011771号