CodeTON Round 7 (Div. 1 + Div. 2, Rated, Prizes!)
A. Jagged Swaps
大致题意
有一个数组,允许选择一个值,其左右两边都是大于当前值的情况下,将当前值和后面的那个值交换一下位置。问是否可能把整个数组排序好
思路
可以从插入排序的方式去考虑,只需要第一个值是对的就行了
AC code
1 |
|
B. AB Flipping
大致题意
有一个 AB 组成的数组,若存在 AB 这样的子字符串,则翻转 AB,且每个下标只能被翻转一次,问最多可以翻转多少次
思路
若存在一堆连续的 AAAABBB
这样的字符串,那么仅最后一个不能进行翻转,其他所有位置都能发生翻转,所以只需要找出这样的连续对数量即可
需要注意的是,如果是 AABBAABB
这种两组的,虽然对于每一个单独的组而言,最后一个不能翻转,但是整体上,除了最后的最后那个,其他也都可以翻转
AC code
1 |
|
C. Matching Arrays
大致题意
有 AB 两个数组,每次任意排序 B 数组,问是否存在一个排列,使得 $a_i > b_i$ 的 $i$ 的数量恰好是 $x$
思路
很简单的一个想法:两个数组排序后,然后将 B 数组的前 $x$ 个值放到后面去即可。然后再判断是否符合预期
AC code
1 |
|
D. Ones and Twos
大致题意
有一个仅有 $1, 2$ 组成数组,每次有两种操作:将其中一个值改成 $1, 2$,问是否存在一个子串,满足求和等于 $x$(x 是每次询问给出的值)
思路
因为数组仅有 $1, 2$ 组成,那么必然,如果总值是 $s$,那么必然可以得到 $s - 2$ 的字串(删掉一侧的值或者删掉两侧的值),
同理也可以得到 $s-4, s-6, \dots$ 直到等于 $0 or 1$
所以只需要维护总和就能解决一般的值了。
而如果需要奇偶性和之和不同,那么必然需要减去一个 $1$,那么只需要找到左右两边最近的 $1$,
然后减去那一侧的 $2$ 和第一个 $1$,就可以得到最大可以满足的和全部之和奇偶性不同的值了,然后可以继续按照上面的推论
AC code
1 |
|
E. Permutation Sorting
大致题意
有一个 $n$ 的排列的数组,每次按照如下操作进行
- 选出其中 $a_i \neq i$ 的 $i$,得到一个由 $i$ 组成的数组 $s$
- $a_{s_{i \space mod \space k+1}} \leftarrow a_{s_i}$
重复进行后,直到整个数组排序完成,问每一个下标完成排序需要操作几次
思路
从题意来看,其实就是每次将没有满足条件的值,右移一格,直到大家都满足了
由于在正常情况下,每次只移动一格,所以需要的成本就等于位置差值
但是因为有别的值会因为满足位置了,就不需要再路过这个节点了,也就可以省去一次移动成本,例如
index | 1 | 2 | 3 | 4 | 5 |
---|---|---|---|---|---|
start | 3 | 5 | 4 | 1 | 2 |
turn 1 | 2 | 3 | 5 | (4) | 1 |
turn 2 | (1) | (2) | (3) | (4) | (5) |
注意到,本来初始为 $5$ 的值,本应该走 $3$ 次才能到目标地点的,但是因为 $4$ 提前到达目标地点,
所以 $5$ 只需要走两次即可,为了方便表示,我们把 $4$ 的移动描述成 $[3,4]$,同理,那么 $5$ 就是 $[2,5]$
故我们需要找到的是,每个值要进行横跨的时候,会同时跨越的其他区间数量,即有哪些节点,他们开始的位置比当前值晚的同时,结束位置还比当前值早
我们可以用线段树来维护这样的值,如果存在一个 $[l,r]$,那么必然可以对所有 $[
那么我们可以将 $[r+1,n]$ 的区间都 $+1$,而如何表示 $<l$,则可以通过访问顺序来控制,我们保证从左往右访问即可,
每次访问后,将当前节点带来的区间进行删除
需要注意的是,因为移动是环形的,所以需要维护两倍区间长度,不然可能会出错
AC code
1 |
|