- 把 1∼n 这 n 个整数排成一行后随机打乱顺序,输出所有可能的次序。
- 输入格式:输入一个整数n。
- 数据范围:n∈[1,9]
- 输出格式:
- 按照从小到大的顺序输出所有方案,每行 1 个。
- 同一行相邻两个数用一个空格隔开。
- 对于两个不同的行,对应下标的数一一比较,字典序较小的排在前面。
for循环里面的i指的是n里面的数字(从1开始循环:满足字典序要求)
假如n=3,数字可以取1,2,3.
由于题目要求字典序较小的排在前面 因此在for循环中从数字1开始填坑
u指的是坑位 第一个坑位从左至右有三种情况:依次可以填1,2,3.
u从1开始:
arr[u] = i;第一个坑位:1/2/3(从左至右的三种情况)
used[i] = true; 表示第一个位置的1/2/3数字已经被使用了 在接下来的分支中不能再用
再执行递归向下分支 dfs(u + 1)
#include<iostream>
#include<algorithm>
#include<cstring>
#include<cstdio>
using namespace std;
const int N = 10;
int n;
int arr[N]; //0表示还没有放数字 1~9表示放了那个数字
bool used[N]; //表示这个数字是否被使用,默认值为false false未使用 true使用
void dfs(int u){
if(u > n){
for(int i = 1; i <= n; i++){
printf("%d ",arr[i]);
}
puts(""); //puts表示输出双引号的值然后回车 此时相当于换行
return;
}
/*
这里的i指的是n里面的数字
假如n=3,数字可以取1,2,3.
由于题目要求字典序较小的排在前面 因此在for循环中从数字1开始填坑
u指的是坑位 第一个坑位从左至右有三种情况:依次可以填1,2,3.
u从1开始:
arr[u] = i;第一个坑位:1/2/3(从左至右的三种情况)
used[i] = true; 表示第一个位置的1/2/3数字已经被使用了 在接下来的分支中不能再用
再执行递归向下分支
*/
for(int i = 1; i <= n ;i ++){
if(!used[i]){
arr[u] = i;
used[i] = true;
dfs(u + 1);
//恢复现场
arr[u] = 0;
used[i] = false;
}
}
}
int main(){
scanf("%d",&n);
dfs(1);
return 0;
}