NOIP Camp #2 比赛记录

NOIP Camp #2

赛时:100+15+5+20

赛后:100+100+100+20

题解

A: 3-格雷码

题意:给定 \(n\),把 \(0...2^n-1\) 中的每个数排成一个环,使得相邻两个位置的数异或起来, popcount=3。\(n\le 23\)

可以用经典格雷码的那个构造,我们先构造 n=4,然后每次倍增。

如何倍增呢?把它复制一遍,左边最高位加上0,右边最高位加上1。但这不一定满足异或起来popcount=3的条件。那咋办呢?

显然,对于一个解,循环位移后依然是一个解(环)。然后我们先找到一个满足条件的位置,然后循环位移把它移动到分界点,就可以满足分界点的条件了。

具体的,设当前是 \(a_1...a_n\)。循环位移,相当于对一个 \(p\),把 \(a\) 变成 \(a_{p+1}...a{n},a_1,a_2...a_{p}\)。找到一个 \(p\),使得 \(pc(a_p\oplus a_1)=2\),且 \(pc(a_{p+1}\oplus a{n})=2\)。然后把 \(p\) 循环位移过去就行了。\(pc\) 表示 popcount。

但这个 \(p\) 不一定能找到。因此,我们每次做完之后,把 \(a\) 随机的循环位移。然后这样就能找到了!(迫真)(还真能)

B

题意:有 \(n\) 个向量,划分成 \(A,B\) 两个集合,选择一些进入 \(A\),剩下的为 \(B\),两个都可以空。设 \(a,b\) 表示 \(A,B\) 集合向量的和。最大化 \(|a-b|\)\(n\le 2\times 10^5\)

最优解的选择一定是:我拿一根过原点的直线劈开所有向量,在一侧的放到A,另一侧的放到B。

这看起来很对,因为这样选择之后,\(a\)\(-b\) 大致上都指向着垂直这根直线的方向,当两个向量是指向同一个方向的时候,它俩加起来模长就会变大。

稍微理性一些,我们发现,如果有一个向量在直线的左侧,且我们的大方向是左A右B,也就是说最后 \(a-b\) 是指向直线左侧的。如果此时我们把一个A中的向量换给B,它显然会让答案变小。

因此,我们把向量按极角排序后,用一个单调队列取和它不超过180°的,更新答案,就一定能取到最优解。

技巧:对于一堆二维的点,顺序不重要的时候,除了考虑按 \(x,y\) 坐标排序,也可以考虑按极角排序,尤其常用于和计算几何有关的题目中

C

你有两个长度位 \(n\) 的序列 \(A,B\)。每次可以选择 \(A\) 中的一个位置,花费 \(1\) 的代价,把它拿出来并插入到前面的任意一个位置。要把 \(A\) 变成 \(B\),最小化花费的代价。保证有解。\(n\le 2\times 10^4\),复杂度 \(O(n^2)\) (oj跑的快)

对于动的问题,我们考虑什么不动。

假设有一些位置一开始就钦定好了不动它们,有 \(m\) 个,答案就是 \(n-m\),加入我们真能做到不动它们。

那一个必要条件是,它们得是公共子序列。但这不充分。

我们考虑,\(A\) 中第一个不动位置之前的那些位置,只会多东西不会少东西。然后再考虑发现,第二个不动位置的前缀,第三个的前缀,...这些集合都是只增不减的。

因此,对于每个不动位置,它在 \(A\) 中的前缀,一定是它在 \(B\) 中前缀的子集。发现,这样就充分必要了。

对着这个dp:像最长公共子序列一样,\(f(i,j)\) 表示 \(A\) 中匹配到 \(i\)\(B\) 中匹配到 \(j\),最多匹配多少个。同样 \(f(i,j)=\max\{f(i-1,j),f(i,j-1)\}\)。如果 \(i,j\) 满足 \(a_i=b_j\),且 \(a[1,i]\subseteq b[1,j]\),那么 \(f(i,j)\) 再用 \(f(i-1,j-1)+1\) 更新。

比赛实况

首先开始玩 \(A\),约1h玩出来了。其实不到1h,因为这里还有我看每道题,各想一会的时间。

B,C 都是我不擅长,或者说,特别不擅长的最优化问题。我的第一反应就是,看起来好简单,但我就是不会啊。鬼才想得到最优策略啊。

然后我就打了两个随机化(注意到我A题也是随机化,那我其实打了3个随机化)。D题是个大毒瘤,但是数论我可能会(?),我就去做了D。但那个题是真毒瘤,NOIp,全场没人过,最高40还是贺的板子。

我这次做题的态度十分消极,不想着去动脑子,想做法,只想着怎么骗到更高分。我记得我看过duyils的博客,里面有一句话可以形容我在干啥:

那时候脑子已经不转了,不想新思路了,只是在东修修,西补补,做些无用的“优化”。与此同时,心理的贪婪又让我停不下这些工作。我后来讲,不要用修修补补、调参乱搞的手头勤快,来掩盖思维的懒惰,这也是很多次比赛后才悟出来的道理。

—— dyls OI生涯回忆与经验分享(更新中)

赛后和rank1的选手简单交流了一下,我觉得还是要手玩。尽管样例水的要死,一眼就看出来了,也应该自己构造几个小样例,玩一玩看看如何达到最优解。

顺便,B题暴露了我的数学基础的欠缺。尽管我知道向量的那些东西,但实际用起来,却还不够熟练到拿这些东西来考虑并解决问题。

posted @ 2021-10-17 08:57  Flandre-Zhu  阅读(43)  评论(0编辑  收藏  举报