今天突然发现同学在做蓝桥杯“寒假作业”那题时,用的是全排列,一下子没看懂,就学习了一下。
参考
http://blog.csdn.net/summerxiachen/article/details/60579623
例如要对0,1,2,3,4五个数进行全排列。输出所有排序结果,及方法总数。
#include<stdio.h>
int a[5] = { 0,1,2,3,4 };
int count = 0;
void swap(int *a, int*b)//交换两个数的值
{
int temp = *a;
*a = *b;
*b = temp;
}
void FullPermutation(int n)
{
if (n == 5)
{
for (int i = 0; i < 5; i++)
{
printf("%d", a[i]);
}
printf("\n");
count++;
}
for (int i = n; i < 5; i++)
{
swap(&a[i], &a[n]);//a[n]为当前需要交换的数,当n=0时,将a[0]分别于a[0]到a[4]交换;但n=1时,a[1]分别与a[1]到a[4]交换
FullPermutation(n + 1);//将下一个数与后面的数交换。
swap(&a[i], &a[n]);//得到一次排序结果后,要讲数还原为初始状态0,1,2,3,4;不然会重复排列。
}
}
int main(void)
{
FullPermutation(0);
printf("%d\n", count);
return 0;
}
上面的递归算法,一上来没看大懂。想起以前室友说过递归都可以装换成for循环,就试了一些。
#include<stdio.h>
int a[5] = { 0, 1 ,2, 3, 4 };
int count = 0;
void swap(int *a, int*b)
{
int temp = *a;
*a = *b;
*b = temp;
}
int main()
{
for (int i = 0; i < 5; i++)
{
swap(&a[i], &a[0]);
for (int i = 1; i < 5; i++)
{
swap(&a[i], &a[1]);
for (int i = 2; i < 5; i++)
{
swap(&a[i], &a[2]);
for (int i = 3; i < 5; i++)
{
swap(&a[i], &a[3]);
for (int i = 0; i < 5; i++)
{
printf("%d ", a[i]);
}
count++;
printf("\n");
swap(&a[i], &a[3]);//交换数之后,再交换回去,回到初始状态,再重新排列。
}
swap(&a[i], &a[2]);
}
swap(&a[i], &a[1]);
}
swap(&a[i], &a[0]);
}
printf("%d\n", count);
return 0;
}