Codeforces Round 864 (Div. 2)
评价:A~E 感觉出的挺一般,特别是 D 怎么放这种暴力题,场上我还没调出来,F 没看。但是 Orz rui_er。
A
在一个点周围放障碍即可。
B
求出最少需要的操作次数 \(p\),若 \(p > k\) 就无解,否则若 \(n\) 为偶数只能任选一个格子翻偶数次,即有解当且仅当 \(2 \mid (k - p)\);若 \(n\) 为奇数可以一直翻中间格子,恒有解。
C
问 \((1,1)\),此时得到了 \(\max(x,y)=p\),再问 \((p,p)\),此时可以得到 \(\min(x,y)=q\),则答案为 \((p,q)\) 或 \((q,p)\)。问 \((p,q)\),若返回值非 \(0\) 那么答案就是 \((q,p)\),否则是 \((p,q)\)。
注意一开始的 \(p > \min(n,m)\) 时要特判,此时已经确定横纵坐标之一了,再问一次 \((1,p)\)(或 \((p,1)\))就可以得出答案。
D
暴力 set
维护每个点的重儿子,\(2\) 操作只会进行 \(O(1)\) 次修改。
E
考虑将每个 \(a_i\) 一直 \(x \gets \varphi(x)\) 得到的所有数从小到大写成一个序列,则问题可以被简化成:
给定 \(n\) 个长度不超过 \(\log V\) 的序列,有两种操作:
- 删除 \([l,r]\) 序列的末尾元素(如果序列只有一个元素就不删)
- 查询 \([l,r]\) 序列的 \(\operatorname{LCP}\)
考虑所有序列总长为 \(O(n \log V)\),删除操作时暴力枚举 \(l\) 到 \(r\) 即可,使用并查集维护每个元素下一个非 \(1\) 元素的位置。
考虑从末尾删元素只会对 \(\operatorname{LCP}\) 在长度方面有影响,所以可以认为是静态查询。
既然是静态,那么对于每个位置预处理出最大的 \(nxt_{k,i}\) 表示 \([i,nxt_{k,i}]\) 在第 \(k\) 位相等。询问直接枚举 \(\operatorname{LCP}\),最大的满足 \(\forall p \in [1,k],nxt_{p,l} \ge r\) 且 \(\forall i \in [l,r], k \le len_i\) 的 \(k\) 就是 \(\operatorname{LCP}\)。
实现时需要一个线段树维护序列长度的区间 \(\min\) 和区间和。时间复杂度 \(O(n (\log n + \log V) + m \log n \log V)\)。
F
考虑建出 \(\min\) 重构树和 \(\max\) 重构树,满足 \(\min\) 重构树上 \(\operatorname{LCA}(u,v)\) 是 \(u,v\) 在原树路径上点权最小值,\(\max\) 上是最大值。
令 \(A\) 为满足第一个条件的点对数量,\(B\) 为满足第二个条件的点对数量,\(C\) 为两个条件都满足的点对数量,则 \(ans = A + B - 2C\)。
\(A,B\) 就是每个点祖先数量和,\(C\) 就是满足 \(\min\) 树上 \(u\) 为 \(v\) 祖先,\(\max\) 树上 \(v\) 为 \(u\) 祖先的 \((u,v)\),树状数组 dfs 序即可。
考虑加点,以该点为端点的向上路径满足第二个条件,只需要让它不满足第一个条件,容斥减去即可。
时间复杂度 \(O(n \log n)\)。