从n个数的当前排列,得到n+1个数的排列,可以这样。
设有排列a,b(a<b)
插入c,可以得到三个排列a<b<c,a<c<b,c<a<b
如果已经确定a<b
那么比较b<c,可以得到排列a<b<c;
否则有b>c,此时比较a<c,可以得到排列a<c<b;
否则有a>c,此时,c<a<b。
把第n+1个需要比较的数插入原来n个数的排列,有n+1种方法,也即把n个数隔开写,得到n+1个空位置,每一个位置的插入得到一个新的排列。
#include<cstdio>
#include<string.h>
#include<stdlib.h>
#include <vector>
using namespace std;
void indent(int n)
{
for(int i=0;i<n;i++)
printf(" ");
}
void make_prog(int cur,int n,const vector<int> &seq)
{
int i;
if(cur==n)
{
indent(n);
printf("writeln(");
for(i=0;i<n;i++)
{
if(i>0) printf(",");
printf("%c",'a'+seq[i]);
}
printf(")\n");
}
else for(i=cur;i>=0;i--)
{
indent(cur);
if(i<cur) printf("else ");
if(i>0)
printf("if %c < %c then",seq[i-1]+'a',cur+'a');
printf("\n");
vector<int>new_seq=seq;
new_seq.insert(new_seq.begin()+i,cur);
make_prog(cur+1,n,new_seq);
}
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("110.txt","r",stdin);
#endif
int m;
scanf("%d\n",&m);
while(m--)
{
int n;
scanf("%d\n",&n);
printf("program sort(input,output);\nvar\n");
printf("a");
int i,j;
for(i=1;i<n;i++) printf(",%c",'a'+i);
printf(" : integer;\nbegin\n readln(a");
for(i=1;i<n;i++) printf(",%c",'a'+i);
printf(");\n");
vector<int>seq;
seq.push_back(0);
make_prog(1,n,seq);
printf("end.\n");
if(m) printf("\n");
}
return 0;
}