CF1621F Strange Instructions 题解
作者:互联网
给出一个 01 串 \(s\),每次可以进行以下操作:
- \(00 \to 0\),收益为 \(a\)。
- \(11 \to 1\),收益为 \(b\)。
- 删除一个 \(0\),代价为 \(c\)。
要求相邻两次操作的型号的奇偶性必须不同,你可以进行任意多次操作,问最后的收益最大值。
\(|s| \le 10^5,1 \le a, b, c \le 10^9\)
贪心
因为 2 是每两次就必须的操作,因此我们考虑之后每次操作后能否继续进行 2 操作,定义势能为字符串中连续的 1 的个数,也就是如果一直进行 2 操作的最多次数,同时也可以发现,操作 \(2\) 具体的位置是不重要的。
那么对于操作 3,如果删除的 \(0\) 是一个孤立的 \(0\)(左右都是 \(1\) 或者边界),并且 \(0\) 旁边都有 \(1\),这样势能就会增加 \(1\),我们以 \(c\) 的代价使得操作 \(2\) 能够进行次数 + 1,因此操作 3 内部的顺序就是 尽量删除中间的孤立 \(0\),最后删除边角的孤立 \(0\)。
注意到 1 、3 操作都是使得 \(0\) 的个数 \(-1\),区别仅在于当这个删除的 \(0\) 是一个孤立的 \(0\) 的时候贡献为 \(-c\),否则为 \(+a\),因此我们只有在删除孤立的 \(0\) 的时候才会使用操作 \(3\),否则就使用操作 \(1\),除非某些情况下必须使用 \(3\) 才能继续进行操作 \(2\),于是 1 、3 操作的顺序确定了下来。
现在考虑操作 \(1\) 之间的顺序,假如现在有若干段 0(非孤立的 0),我们一定是先从中间的最短一段 \(0\) 下手,这样才会有更多机会创造孤立 \(0\),进而使得操作 2 继续进行。
整理一下:
如果我们要进行 \(2\) 操作:
- 能动就动。
- 否则游戏终止。
如果我们要进行 \(1\) 操作:
- 如果当前的势能已经到了 \(0\),现在就属于游戏进行的生死存亡时刻:
- 不玩了,最后捞一笔钱,如果能进行 1 操作,则进行,然后结束游戏。
- 继续玩,删除一个中间的孤立 \(0\),游戏继续。
- 势能 \(>0\),现在不急,可以
水时长,同时进行一些储备,于是肯定是优先考虑 \(1\) 操作:- 如果还有 \(0\) 的段,那么我们从中间的段中挑一个最短的进行操作 \(1\),这样有利于后面继续操作。
- 中间没有的话就从边上的一段进行操作 \(1\)。
- 实在不行,只能使用操作 \(3\),删除中间孤立 \(0\),顺便使得势能 \(+ 1\)。
- 还是实在不行就从边上进行操作 \(3\),但是势能不变。
- 玩不下去了,终止游戏。
选择最短的段可以预先排序然后维护栈解决,时间复杂度 \(\mathcal O(n \log n)\)。
标签:势能,孤立,删除,题解,游戏,Strange,操作,CF1621F,进行 来源: https://www.cnblogs.com/werner-yin/p/solution-cf1621f.html