原文代码地址:
http://blog.csdn.net/morewindows/article/details/7370155(原文很详细,博主很强大!)
//全排列的递归实现
#include <stdio.h>
#include <string.h>
#include<iostream>
using namespace std;
void Swap(char *a, char *b)
{
char t = *a;
*a = *b;
*b = t;
}
//k表示当前选取到第几个数,m表示共有多少数.
void AllRange(char *pszStr, int k, int m)
{
static int count=0;
count++;
if (k == m)
{
cout<<"#"<<count<<" "<<k<<endl;
static int s_i = 1;
printf(" 第%3d个排列\t%s\n", s_i++, pszStr);
}
else
{
cout<<"*"<<count<<" "<<k<<endl;
for (int i = k; i <= m; i++) //第i个数分别与它后面的数字交换就能得到新的排列
{
cout<<"$"<<count<<" "<<k<<" "<<i<<endl;
Swap(pszStr + k, pszStr + i);
AllRange(pszStr, k + 1, m);
Swap(pszStr + k, pszStr + i);
cout<<"@"<<count<<" "<<k<<" "<<i<<endl;
}
}
}
void Foo(char *pszStr)
{
AllRange(pszStr, 0, strlen(pszStr) - 1);
}
int main()
{
printf(" 全排列的递归实现\n");
printf(" --by MoreWindows( http://blog.csdn.net/MoreWindows )--\n\n");
char szTextStr[] = "123";
printf("%s的全排列如下:\n", szTextStr);
Foo(szTextStr);
getchar();
return 0;
}
由于源代码递归,初学者很难看懂到底递归到那里去了,怎么递归的,又是怎么实现全排列的等等一系列问题,通过看上图,再加上在纸上画一画,估计会好理解很多的。
由上图可见,1,2,3.....10为调用AllRange函数的次数,对应不同位置,我用了不同的符号标注,并输出了 i k 的值,发现了如下规律:
先输出了 123 ,132 后,通过swap又将 132 转为了 123,
接着是输出了 213,231(即对123进行了第一位与第二位交换,再进行了第二位与第三位交换),然后又把 231 转为了123,
接着输出321 ,312。
这种递归的算法,我感觉我作为初学者,一次肯定理解不到位,多学才行啊。
还有一种神奇的方法,C++强大的STL,可以通过调用next_permutation函数完美解决。
贴上代码,大家欣赏:
#include <iostream>
#include <algorithm>
#include <string>
using namespace std;
int main()
{
string str;
cout<<"请输入:";
cin >> str;
sort(str.begin(), str.end());
cout<<"全排列结果:"<<endl;
cout << str << endl;
while (next_permutation(str.begin(), str.end()))
{
cout << str << endl;
}
system("pause");
return 0;
}