Atcoder ARC-064

ARC064(2020.7.23)

A

直接贪心即可。

B

手玩样例可以猜出这样一个结论,如果两端字符相同,如果字符串长度为奇数那么后手赢,否则先手赢,两端字符不同则相反。证明的话先从特殊情况开始入手,假如只存在一种字符出现了多次(除去两端字符的出现次数)因为保证了开始的字符串是合法的,那么这种出现多次的字符出现次数一定不超过字符串长度的一半,于此同时我们要明确一个观点,两个人肯定不会让自己在当前很快输掉,这是显然的,因此两个人都会尽可能往后走,可以发现如果将出现多次的字符全部拿走那么最终的胜利状态将是固定的,那么固定胜利的这个人一定会将这些字符全部拿走因为字符数量少于总长的一半因此他是可以做到的,所以这种特殊情况下上面的结论是正确的。再考虑多种字符出现多次的情况,同样的固定赢的那个人同样可以取走出现多次的那些字符以保证自己必胜,因此上面的结论就正确了。

C

将原问题中的圆,起点终点都抽象成 \(n + 2\) 个点,两圆之间的距离就是圆心距离减去两圆半径(特殊地如果小于 \(0\) 那么距离为 \(0\)),起点终点和其他圆的距离就是两点之间的距离减去圆的半径,注意还需要考虑从起点直接走到终点的情况,因此还需要在起点和终点之间连边边权为两点间距离,最后跑一遍最短路即可。

D

看到题目以后我们猜测,是不是所有回文串对答案的贡献都是其长度呢?手玩之后可以发现这个是错的,比如 \(abaaba\) 对答案的贡献显然只有 \(3\),不难发现这种串是有循环节的,那我们又可以大胆猜测所有回文串对答案的贡献是否是其最小循环节的长度呢?实际上这也是不对的,比如 \(abbaabba\) 对答案的贡献其实只有 \(2\) 因为操作两次以后会是一个新的回文串我们也会枚举到,但是我们发现如果最小循环节长度为奇数,那么貌似贡献都是最小循环节长度而如果长度为偶数贡献都是长度除以 \(2\),事实上这个结论是正确的,下面我们来证明这个结论。

下面令 \(r_s\)\(s\) 的反串,最小循环节长度为 \(d\)

  • 一个回文串的每个循环节也是回文串

这个根据定义很容易可以得出证明。

  • 每进行一次操作相当于对最小循环节进行了一次操作

这个结论也比较显然,手玩可以证明

  • 一个串不论进行多少次操作其最小循环节长度不变

根据上一条性质可以发现,每次我们最小循环节的长度都不会变大,如果我们在某次操作后最小循环节长度变小了,根据我们最开始的定义这个变小的最小循环节的串一定可以再经过若干次操作变回原串,此时最小循环节长度变大,矛盾。

  • 最小循环节长度不同的两个串不会互相影响

上个结论的推论

  • 对一个串执行 \(k\) 次操作和执行 \(d - k\) 次操作后的两个串互为反串

根据性质一二不难得出证明。

  • 一个串如果对答案的贡献会记重当且仅当存在一个 \(k\) 使得 \(k = d - k\)

考虑答案什么时候会被记重,当且仅当执行一些操作后重新变回一个回文串,根据性质一五容易证明。

根据性质 \(4, 5\) 就验证了上面我们对每个回文串对答案贡献的猜想。下面我们只需要考虑如何统计最小循环节为 \(d\) 的回文串数量即可。不难发现一个回文串只要确定前 \(\lceil \frac{d}{2} \rceil\) 个位置的数就可以确定一个回文串,且前 \(\lceil \frac{d}{2} \rceil\) 可以任意填数,但是直接这样计数是不正确的,因为我们要统计的是最小循环节为 \(d\) 的答案,而这样算出来的回文串数量是存在循环节长度为 \(d\) 的数量,因此我们还需要枚举 \(d\) 的约数,将其约数的答案减去即可。

posted @ 2020-09-15 22:10  Achtoria  阅读(127)  评论(0编辑  收藏  举报