递归方法求不重复排列

2014-11-24 03:07:18 · 作者: · 浏览: 1

[cpp]
/*******************************************************************\
输入n个数,输出由这n个数构成的排列,不允许出现重复的项
输入:
3
1 1 2
输出:
1 1 2
1 2 1
2 1 1
思路:
先手工模拟排列的过程,在第三个排列2 1 1中,我们之所以能够写出来,是因为
我们能发现1和2是不同的数,而计算不能,因此在存储数据的时候数组中不能有
重复的数据,因此存储的数比实际的数据个数要少,因此要用辅助数组记录每个
元素的个数,这样就能利用不含重复元素的排列算法求解.
\*******************************************************************/
#include
#include
#include

const int maxn = 100;

int num[maxn];
int used[maxn];
int ans[maxn];
int n, m;

int readdata()
{
memset(used, 0, sizeof(used));
memset(num, 0, sizeof(num));
memset(ans, 0, sizeof(ans));
int i = 0, j = 0;
if(scanf("%d", &n) == EOF || n <= 0)
return false;
int val = 0;
for(i=0; i {
scanf("%d", &val);
for(j=0; j {
if(num[j] == val)
{
used[j]++;
break;
}
}
if(j == m)
{
num[m] = val;
used[m] = 1;
m++;
}
}
return true;
}

void output()
{
for(int i=0; i {
if(i < n-1)
printf("%d ", ans[i]);
else
printf("%d\n", ans[i]);
}
}

void unrepeatPerm(int dep)
{
if(dep >= n)
{
output();
return;
}
for(int i=0; i {
/*最好是手写模拟递归过程,其中num数组中存储的是不同的元素,这也是关键,*/
if(used[i] > 0)/*此处是重点*/
{
used[i]--;
ans[dep] = num[i];
unrepeatPerm(dep+1);
used[i]++;
}
}
}

int main()
{
while(readdata())
{
unrepeatPerm(0);
}
return 0;
}

/*******************************************************************\
输入n个数,输出由这n个数构成的排列,不允许出现重复的项
输入:
3
1 1 2
输出:
1 1 2
1 2 1
2 1 1
思路:
先手工模拟排列的过程,在第三个排列2 1 1中,我们之所以能够写出来,是因为
我们能发现1和2是不同的数,而计算不能,因此在存储数据的时候数组中不能有
重复的数据,因此存储的数比实际的数据个数要少,因此要用辅助数组记录每个
元素的个数,这样就能利用不含重复元素的排列算法求解.
\*******************************************************************/
#include
#include
#include

const int maxn = 100;

int num[maxn];
int used[maxn];
int ans[maxn];
int n, m;

int readdata()
{
memset(used, 0, sizeof(used));
memset(num, 0, sizeof(num));
memset(ans, 0, sizeof(ans));
int i = 0, j = 0;
if(scanf("%d", &n) == EOF || n <= 0)
return false;
int val = 0;
for(i=0; i {
scanf("%d", &val);
for(j=0; j {
if(num[j] == val)
{
used[j]++;
break;
}
}
if(j == m)
{
num[m] = val;
used[m] = 1;
m++;
}
}
return true;
}

void output()
{
for(int i=0; i {
if(i < n-1)
printf("%d ", ans[i]);
else
printf("%d\n", ans[i]);
}
}

void unrepeatPerm(int dep)
{
if(dep >= n)
{
output();
return;
}
for(int i=0; i {
/*最好是手写模拟递归过程,其中num数组中存储的是不同的元素,这也是关键,*/
if(used[i] > 0)/*此处是重点*/
{
used[i]--;
ans[dep] = num[i];
unrepeatPerm(dep+1);
used[i]++;
}
}
}

int main()
{
while(readdata())
{
unrepeatPerm(0);
}
return 0;
}