题目描述
有4个互不相同的数字,输出由其中三个不重复数字组成的排列。
输入格式
4个整数。
输出格式
所有排列
解法1
解题思路:
首先定义一个数组,将四个数存入数组。
由于是将三个数排列,所以可以先将其中一个数拿走(也就是在排列时不让其中一个参与),这里利用for循环从后往前(因为题中给的样例输出的时候是从小到大按顺序输出的)依次拿走一个数,排列剩余三个。
对剩余三个排列时用三重for循环:
第一重表示选取第一个数(这个数不可以等于拿走的那一个,故if (i !=j),如果等于就成四个数排列了);
第二重表示选取第二个数(这个数不可以等于获取的第一个数和拿走的那个数,故if (j != k&&k!=i),如果等于就出现重复数字了);
第三重表示选取第三个数。
这三重for循环均依次从数组中第一个数往后循环,因为题目输出样例中的顺序是从小到大依次输出的。
#include<iostream>
using namespace std;
//有4个互不相同的数字,输出由其中三个不重复数字组成的排列。
int main()
{
int arr[4];
for (int i = 0; i < 4; i++)
{
cin >> arr[i];
}
//用一个数组装4个数,分别将其中一个数拿走,将剩余三个全排列
for (int i = 3; i >= 0; i--)//从最后一个开始依次拿走
{
for (int j = 0; j < 4; j++)//获取第一个数,从第一个遍历
{
if (i !=j)//i等于j的时候就跳过
{
for (int k = 0; k < 4; k++)//获取第二个数,从第一个遍历
{
if (j != k&&k!=i)//但因为不允许有重复,所以当k=j且k=i时不能进入循环
{
for (int l = 0; l < 4; l++)//获取第三个数
{
if (l != i && l != j && l != k)//第三个数不能与前面获取的数相同,相同就跳过
{
cout << arr[j] <<" " << arr[k]<<" " << arr[l] << endl;
}
}
}
}
}
}
}
return 0;
}
解法2
解题思路:提供一种顺序正确的做。观察输出结果,可以分为4组;第一组没有4,第二组没有3,第三组没有2,第四组没有1。解决方法,分为4组,从第一组开始,使用dfs算法。dfs中有两个参数cur,cont.cur用来标记下标,cont表示想要跳过的(这组里面没有的数字)。
注意事项: dfs算法得到一个解后,记得return.
参考代码:
#include<iostream>
using namespace std;
int book[5];
int v[4], k[5];
void dfs(int cur,int cont)
{
int i;
if (cur == 4)
{
for (i = 1; i <= 3; i++)
{
cout << v[i]<<" ";
}
cout << endl;
return;
}
for (i = 1; i <= 4; i++)
{
if (book[i] == 0 && i!=cont)
{
book[i] = 1;
v[cur] = k[i];
dfs(cur + 1,cont);
book[i] = 0;
}
}
return;
}
int main()
{
int i;
for (i = 1; i <= 4; i++)
cin >> k[i];
dfs(1, 4);
dfs(1, 3);
dfs(1, 2);
dfs(1, 1);
return 0;
}