Codeforces Round 668 (Div. 2)
做题情况
7 分钟 A,23 分钟 B,然后想了一场 C,D 直接跳过不看,E 有了初步思路但不大会写
A. Permutation Forgery
解题思路
猜结论:直接把序列反转即可
手玩了一下确实是对的
代码实现
1 |
|
B. Array Cancellation
解题思路
仍然先手玩一下,发现一个初步性质:
对于一个正数,应把它转移到它后面的第一个负数,转移完后剩下的正数之和即为答案
紧接着发现这个性质可以变得更简单一些:
对于一个正数,也可以把它转移给它后面的第一个正数,然后让那个正数往后转移,答案不变
所以我们可以确定最终做法:
对于一个正数,应把它转移到它的下一个数,转移完后剩下的正数之和即为答案。
代码实现
1 |
|
C. Balanced Bitstring
解题思路
手玩的时候可以发现一个很重要的性质(反正我没发现):
一个字符串为 (0-indexed) k-Balanced Bitstring 的必要条件是:第 i 位与第 i mod k 位的字母相同。
这个性质比较好理解,因为如果 s[i..i + k - 1]这个区间内的字符串为 k-Balanced Bitstring 的话,那么这个窗口在往后移一格时,为了保证下一个区间也是 k-Balanced Bitstring,就需要满足扔掉的字符(s[i])和加进来的字符(s[i + k])相同,才能不改变 0 数和 1 数的关系。
有了这个性质,我们就可以从前往后扫一遍,将问号分成三类:需要填 0 的、需要填 1 的、不确定的。如果一个模 k 相等的位置同时需要填 0 和 1,就出现了矛盾直接 fail。最后统计一下,判断一下不确定的位置够不够用就行了。
代码实现
1 |
|
D. Tree Tag
解题思路
先考虑初始情况,如果 Alice 一步就能到达 Bob 那就肯定没戏,即 。
再考虑极限情况。一条长为 的链时,Alice 肯定会不断把 Bob 往绝路逼,那么 Bob 只有一步跨过 Alice 才能有赢的机会,也就是 ,否则就直接凉凉。另外,注意到如果 ,那么 Alice 两步可以到的点覆盖了整条链,Bob 无处可逃。
然后推广一下极限情况到树上。注意到树最长的链是(假设长为 )直径,那么如果 ,Bob 躲到直径上就可以一直逃脱 Alice 的追捕。反之,如果 ,那么 Alice 只要站到重心上,就可以覆盖整棵树,Bob 仍然无路可逃。
最后总结一下:当且仅当下列三个条件至少有一个满足时,Alice 一定胜利,否则 Bob 一定胜利。
- 树的直径
那么代码就一个 DFS 就完事了。
代码实现
1 |
|
E. Fixed Point Removal
解题思路
手玩一下可以发现一个事:一次删除应是删除最后一个能删除的数,这样不会影响到前面可以删除的数字,后面的数字说不定也能删了,稳赚不亏
精确描述一下:
对于一个数 ,它能被删除的条件是 。(这里编号是随着删除而移动的)
那么我们干脆重定义并动态维护 ,表示这个数被删的条件是在前面删几个数,如果是 0 就可以直接删,如果是负数就说明永远删不了,不妨令其为 n + 1。
怎么维护?
上面是我考场上想出的东西,下面是看题解才学会的东西。
其实可以直接拿线段树维护 。具体地,我们把操作离线下来,并按照左端点从大到小排序,依次考虑从左边加入一个数会造成什么影响。
对于我们加入的一个数 ,
- :可以删,把这个数设为已删的状态()并加入树状数组,后面所有数集体 -1
- :不能删,加进去线段树维护。
然后用树状数组查询答案就行了。
代码实现
1 |
|
- 本文作者:Handwer STD
- 本文链接:https://blog.handwer-std.top/2020-10-27/CF1405/index.html
- 版权声明:本博客所有文章均采用 BY-NC-SA 许可协议,转载请注明出处!