2023 年 12 月训练记录
2023 年 12 月训练记录
怎么就寄了呢。
没救了。
不能再摆了。
CF1824E LuoTianyi and Cartridge
我们对最小值做扫描线,现在就转化成了使得 \(\sum b+\sum d\) 最大。
我们考虑点与边合法的充要条件。
注意到假设有 \(k\) 个点,\(k-1\) 条边,只要满足对于每条边的两部分都有点就是合法的,否则不合法。
这显然是必要的,充分性的话,就是考虑除非整个图连通,否则一定存在两个点,分别在这条边的两部分,并且它们不在同一个连通块内。
假设当前有 \(p\) 个点,\(e\) 条边,并且每条边两部分都有点。
如果 \(p-1<e\),则说明点可以全选,边直接保留前 \(p-1\) 大即可。
否则,可以证明边一定全选。那么对于每条边都要求它的两端都要选点。我们把边按照其深度教大的点,放到 DFS 序上考虑。那么也就是要在每个区间内和区间外都有选点。
注意到 DFS 序要么不交,要么包含,所以也就是所以极小的 DFS 序区间,要在这里面选一个点。如果存在一个区间包含所有区间,则还得再外面再选一个点。
整个过程都是可以 \(O(n\log n)\) 来维护的。
记录。
CF1824D LuoTianyi and the Function
提供一个树状数组做法。
orz kcudcigam
注意到求的是历史和,那不妨就转化成 \([1,r]\) 减去 \([1,l-1]\)。
考虑维护关于行的一次函数,答案表示为 \(ans=kx+b\),用一个数据结构维护 \(k\),一个数据结构维护 \(b\)。
那每添加一个数,就相当于 \(K\) 和 \(B\) 上的区间加,然后查询就是查的区间和。
然后使用区间加,区间和的树状数组来支持 \(K\) 和 \(B\) 即可。
注意到区间加,区间和也是维护一次函数,用两个树状数组来实现,所以总共用了 \(4\) 个树状数组。
时间复杂度 \(O(n\log n)\)。
记录。
CF1464F My Beautiful Madness
注意到所有路径中,假设深度最深的 LCA 为 \(x\)。
则所有路径的 \(d\) 邻居有交,当且仅当 \(x\) 的 \(d\) 级祖先 \(y\) 与路径的 \(d\) 邻居有交。
证明:首先把 \(y\) 往上拉 \(x\) 就不合法了。由于 \(x\) 是深度最深的 LCA,所以 LCA 在 \(y\) 子树内的一定合法,所以把 \(y\) 往下拉是没有意义的。
所以我们只需要判断 \(x\) 是否合法。由于 LCA 在 \(y\) 子树内的都合法,所以我们只需要考虑 LCA 在 \(y\) 子树外的了。
令 \(y\) 的 \(d\) 级祖先为 \(z\)。
-
LCA 在 \(z\) 子树外。
- 如果这条路径跟 \(z\) 的子树不交,则不合法,这是好判的,我们用 BIT 在 DFS 序上维护树上差分即可;
- 如果这条路径跟 \(z\) 的子树有交,则合法,因为这条路径一定经过 \(z\);
-
LCA 在 \(y\) 到 \(z\) 的路径上。
这种情况必然合法。
-
LCA 不在 \(y\) 到 \(z\) 的路径上,但在 \(z\) 的子树内。
则到 \(y\) 的最近点为其 LCA。
由于在路径上的 LCA 必定合法,所以我们就只需要求 LCA 在 \(z\) 子树内的到 \(y\) 的最大距离。直接在 DFS 序上,用线段树维护直径即可。
使用 \(O(n\log n)\) \(O(1)\) LCA,时间复杂度 \(O(n\log n)\)
记录。
CF1411G No Game No Life
首先,我们可以对这个 DAG,\(O(n+m)\) 的求出所有点的 SG 值。然后,问题就转化成了有一个变量 \(x\),初始为 \(0\),每次选随一个 \([1,n+1]\) 的数 \(y\),如果 \(y\in[1,n]\),则 \(x\leftarrow x \oplus sg_y\),否则结束。
问结束时,\(x= 0\) 的概率,这样就能求输的概率,然后就求出了赢的概率。
注意到 \(m\) 条边的 SG 值,不超过 \(O(\sqrt{m})\),所以 SG 的值域是 \(O(\sqrt{m})\) 级别的,在本题中就是 \(512\)。
所以,我们可以列状态 \(f_i\) 表示当前变量 \(x=i\),最后 \(x=0\) 的概率。
然后对这个高斯消元即可求出答案。
时间复杂度 \(O(m\sqrt{m})\)。
不过有更优秀的做法,给 gxy001 大神磕头了。
令 \(f_i\) 表示一次操作使得 \(x\leftarrow x\oplus i\) 的概率。令 \(g_i\) 表示最终 \(x=i\) 的概率。
我们考虑对 \(1-F\) 求异或卷积逆即可得到答案。
对于异或卷积,有逆当且仅当 FWT 后每一项都非 \(0\)。
那么考虑 FWT 的过程,\(f'_i=\sum_{j=0}^{2^k-1} (-1)^{\text{popcount}(i\ \text{and} \ j)} f_j\),每一项 \(f_j\) 对于 \(f'_i\) 的贡献都是 \(\pm 1\)。
注意到这个常数项 \(1\) 相当于给每项都加了 \(1\),因为 \(\text{and}\) 出来是 \(0\)。
由于 \(0\le f_i\le \sum_{i=0}^{2^k-1} f_i<1\),所以 \(0<f'_i<2\) 的。
所以有逆。
于是我们只需要对 \(F\) 做一次 FWT,然后对点值求逆,然后再 iFWT 回去即可。
时间复杂度 \(O(n+m+\sqrt{m}\log m)\)。
记录。
注意到这个做法,可以对所有的最后的 \(x\) 求出答案。
深入思考:对于异或卷积来讲,如果有逆,则逆是有限的;而对于多项式求逆来讲,逆是无限项的,所以直接对点值求逆,求出的是循环逆,相当于是在模 \(x^n -1\) 意义下的,而不是在模 \(x^n\) 意义下的。
CF1912F Fugitive Frenzy
orz zmx
假设当前警察在 \(i\),我们考虑先让小偷先确定出在每个叶子 \(j\) 的概率,假设是 \(p_{i,j}\)。
令 \(f_i\) 表示警察当前在 \(i\) 节点,抓到小偷的最小步数。
那么注意到警察的策略一定是选择一个叶子 \(j\),因为小偷已经确定好了,所以在警察到叶子 \(j\) 前不会乱动,所以抓到小偷的概率为 \(p_{i,j}\),所以 \(f_i=(1-p_{i,j})f_j+dis_{i,j}\)。
注意到答案一定是分数,如果做法跟精度无关,完全可以出成取模。
上面都是赛时想到的部分,下面都是 zaozao_zmx 大神很厉害的求解方法。
注意到 \(p_{i,j}\) 的元太多了,我们移项,得到 \(p_{i,j}=\frac{-f_i+f_j+dis_{i,j}}{f_j}\)。
注意到 \(\sum_{j\ne i} p_{i,j}=1\),所以,\(\sum_{j\ne i} \frac{-f_i+f_j+dis_{i,j}}{f_j}=1\)。
想求解 \(f_i\),我们可以初始时令 \(f_i=1\),这是因为我们有除法,所以我们避免 \(0\)。
然后随机一个位置 \(i\),根据这个等式求出 \(f_i\),把这个过程执行 \(10^6\) 次即可。