(zay)讲的题
luogu CF1352G Special Permutation
luogu CF1352G Special Permutation
题目描述
给定 (t) 组数据,每组数据包含一个整数 (n)。
对于每个整数 (n),你需要输出一个长度为 (n) 的全排列 (p),输出要求对于所有满足 (i in [1,n))的 (i),有 (|p_i - p_{i+1}| in [2,4]),如果不存在,输出 (-1),对于每一组数据,输出占一行。
如果有多组解,请输出其中任意一个。
样例
(in)
6
10
2
4
6
7
13
(out)
9 6 10 8 4 7 3 1 5 2
-1
3 1 4 2
5 3 6 2 4 1
5 1 3 6 2 4 7
13 9 7 11 8 4 1 3 5 2 6 10 12
思路:
先随便分析一下:对于n = 8,我们可以这样构造:
[1 3 5 7 4 8 6 2
]
对于n = 7,我们可以这样构造:
[1 3 5 7 4 6 2
]
那如果有数字(x = 8(or 7) + 2k (k in Z^*)),我们能够通过在两边加1、2,然后把整个数组的所有数字都加2构造出来。
对于小于等于6的n,我们可以直接next_permutation
(Code)
int t,n;
int a[2000];
int main(){
// cout << "I AK IOI" << endl;
// cout << "IOI AK I" << endl;
// cout << "CYCYCYC" << endl;
// cout << "YCYCYCY" << endl;
cin >> t;
while(t--){
cin >> n;
for(int i = 1;i <= n; i++) a[i] = i;
if(n == 1){
cout << -1 << endl;
continue;
}
if(n <= 6){
bool F = 0;
do{
bool flag = 0;
for(int i = 2;i <= n; i++){
if(abs(a[i] - a[i-1]) > 4 || abs(a[i] - a[i-1]) < 2) flag = 1;
}
if(flag == 0) break;
if(!next_permutation(a+1,a+1+n)){F = 1;break;}
}while(1);
if(!F){
for(int i = 1;i <= n; i++) cout << a[i] << ' ';
cout << endl;
}else cout << -1 << endl;
continue;
}else if(!(n & 1)){
for(int i = 1;i <= n/2; i++) cout << 2 * i-1 << ' ';
cout << n-4 << ' ';
cout << n << ' ';
cout << n-2 << ' ';
for(int i = n/2 - 3;i >= 1; i--) cout << i * 2 << ' ';
cout << endl;
}else{
for(int i = 1;i <= n/2+1; i++) cout << 2 * i-1 << ' ';
cout << n-3 << ' ';
cout << n-1 << ' ';
for(int i = n/2 - 2;i >= 1; i--) cout << i * 2 << ' ';
cout << endl;
}
}
return 0;
}