bdfz_2024_summer/day8/T493943/T493943.md

3.9 KiB
Raw Blame History

通关

题目描述

在你的面前是一个 n 个珠子的关卡。这些珠子排成一行,编号 $1 \sim n$,已知初始从左到右第 i 个珠子是编号 p_i.

由于你只有两只手,所以你每次可以拎出任意 2 个珠子(不一定相邻)并将它们交换位置,你将要将这 n 个珠子最终排成从左到右依次为 1 \sim n 的顺序,这样才可以通关。

在你觉得这是个简单题的时候你突然在关卡的旁边读到了这样一句话:

特别注意:每个珠子有一个特定的颜色。由于同种颜色之间有强相互作用力,假如你某次拎出的 2 个珠子是同一颜色,那么会相互吸引从而产生爆炸,因此每次都必须交换 2 个颜色不同的珠子。

这下你突然对这个关卡开始感兴趣了,你打算着手来解决这个问题。关卡开发人员已经通过 O(100000^{100000!}) 的复杂度的算法提前计算出了最少步数,你需要构造一组方案使得尽量接近这个最少步数,具体详见评分标准。

输入格式

第一行两个数 n,type=0/1.

第二行 n 个数,第 i 个数为 p_i.

第三行 n 个数,第 i 个数表示从左到右i 个球的颜色编号,设为 c_i.

输出格式

若 $type=0$,则需要输出可行方案的最小步数。否则,输出任意一个可行步数均可。但不管 type 是多少,都需要保证这个步数不超过 $1 \times 10^6$。

接下来步数行,每行两个数 x,y 以空格分隔,表示这次交换你要交换位于左数第 x 个和第 y 个的珠子。需要注意必须要保证这些输出的行数等于第一行输出的数,否则 checker 会直接退出。

假如构造不出 \leq 1 \times 10^6 次操作的方案,输出一个 -1 即可。

样例 #1

样例输入 #1

4 0
2 1 4 3 
2 1 3 4

样例输出 #1

2
1 2
3 4

样例 #2

样例输入 #2

6 1
3 5 4 6 1 2 
4 5 1 1 1 6

样例输出 #2

5
1 2
1 5
2 3
4 6
2 4

样例 #3

样例输入 #3

23 1
14 8 23 19 6 9 5 22 20 15 1 11 21 13 18 12 16 4 17 2 3 7 10
3 5 5 1 5 5 2 2 5 1 2 5 3 1 1 1 4 3 5 2 5 5 4

样例输出 #3

35
11 1
20 2
11 21
21 3
11 3
18 4
7 5
4 7
7 6
4 6
4 22
22 7
4 7
20 8
4 22
22 9
4 9
23 10
12 11
16 12
14 13
3 16
16 14
3 14
4 23
23 15
4 15
17 16
19 17
4 23
23 18
4 18
23 19
22 20
23 21

样例 #4

样例输入 #4

见下发样例

样例输出 #4


提示

本题使用 checker 来评判你的得分。本题下发文件中有一份可使用的 checker.cpp 和配套的 testlib.h 文件,想要使用 checker 你需要执行如下几步:

  1. testlib.hchecker.cpp 放至同一文件夹下,使用 C++11 编译 checker.cpp 获得可执行文件。

  2. 将输入文件,答案文件和自己的输出文件放至同一文件夹下,使用命令行定位到该目录。

  3. 使用语句 ./checker <input-file> <output-file> <answer-file> 运行 checker 得到评判结果。

    例如,设输入文件,答案文件和输出文件分别叫做 pass.in,pass.out,mypass.out

    只需要运行语句:./checker pass.in pass.out mypass.out

  4. 假如输出文件能够在该测试数据下得分,那么 checker 会回复 ok,否则会给出对应错误提示。

    需要注意你的代码不应依赖于 checker,为此 checker.cpp 文件做了模糊化处理。

本题使用 Subtask 评测,第 5 个子任务完全依赖第 1 个子任务。

子任务分值 特殊限制
10 n \leq 8
10 $n \leq 10^5$c_i 是一个排列
20 n \leq 10^5,type=1
20 n \leq 10^5,p_i=i\%n+1
40 n \leq 10^5

对于全部数据,1 \leq c_i \leq n