全排列的生成算法(七)——递归算法
当排列采用递归方式定义时,可以直接从他的定义出发来生成全体排列。
如果用P表示n个元素的排列,而Pi表示不包含元素i的排列,(i)Pi表示在排列Pi前加上前缀i的排列,那么,n个元素的排列可递归定义为:
如果n=1,则排列P只有一个元素i
如果n>1,则排列P由排列(i)Pi构成(i=1、2、....、n-1)。
根据定义,容易看出如果已经生成了k-1个元素的排列,那么,k个元素的排列可以在每个k-1个元素的排列Pi前添加元素i而生成。例如2个元素的排列是1 2和2 1。要产生3个元素的排列,P1是2 3和3 2,在每个排列前加上1即生成1 2 3和1 3 2两个新排列,类似的,P2则是1 3和3 1,P3是1 2和2 1,按同样方法可生成新排列2 1 3、2 3 1和3 1 2、3 2 1。从而可以得到3个元素的全体排列。
//递归算法
//输入:排列元素个数n
//输出:n个元素的排列
#include<iostream>
#include <iomanip>
using namespace std;
void perm(int *,int,int);
void output(int *,int);
int total;
int main(void)
{
freopen("in.dat","r",stdin);
int n,*p;
while(cin>>n)
{
p=new int[n];
for(int i=0;i<n;i++)
p[i]=i+1;
total=0;
perm(p,n,0);
}
return 0;
}
void perm(int *p,int n,int k)
{
if(k==n)
output(p,n);
for(int i=k;i<n;i++)
{
swap(p[i],p[k]);
perm(p,n,k+1);
swap(p[i],p[k]);
}
}
void output(int *p,int n)
{
cout<<setw(5)<<++total<<": ";
for(int i=0;i<n;i++)
cout<<setw(3)<<p[i];
cout<<endl;
}