两排列组合问题的非递归求解

问题一:

打印1,2—n中所有满足1<=i1<i2<–<ik<=n(k<=n)的有序数组(i1, i2,—ik)并输出,要求用非递归方法解决.

代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63

#define N 6
#define K 4

void ()
{
int a[K];
bool TF;
int i, j;

i=0;
TF=false;
while(1)
{
if (i==0)
{
if (TF==false)
{
a[i]=1;
}
else
{
a[i]++;
}

if (a[i]>N-K+1)
break;
i++;
TF=false;
continue;
}
else
{
if (TF==false)
a[i]=a[i-1]+1;
else
{
a[i]++;
if ((a[i]-a[i-1])>(N-a[i-1])-(K-i)+1)
{
i--;
TF=true;
continue;
}
}

if (i==K-1)
{
for (j=0; j<K; j++)
{
printf("%d ", a[j]);
}
printf("n");

TF=true;
continue;
}
i++;
TF=false;
continue;
}
}
}

 

问题二:打印所有n元排列,非递归解决
代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77

#define N 5
int first(int index, int number[]);

void ()
{
int a[N]={0};
int number[N]={0};
int i, j, temp;
bool TF;

i=0;
TF=false;

while(1)
{
if (i==0)
{
if (a[i]!=0)
number[a[i]-1]=0;
a[i]++;

if (a[i]>N)
break;

number[a[i]-1]=1;
i++;
TF=false;
continue;
}
else
{
temp=first(a[i], number);
if (temp==0)
{
number[a[i]-1]=0;
a[i]=0;
i--;
TF=true;
continue;
}

if (TF)
{
number[a[i]-1]=0;
}
a[i]=temp;
number[a[i]-1]=1;

if (i==N-1)
{
for (j=0; j<N; j++)
{
printf("%d ", a[j]);
}
printf("n");
continue;
}

i++;
TF=false;
continue;
}
}
}

int first(int index, int number[])
{
int i;
for (i=index; i<N; i++)
{
if (number[i]==0)
return i+1;
}

return 0;
}

 问题一的递归代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91

#include <malloc.h>
#include <stdlib.h>
void DY(int *p, int k, int n);
int C(int n, int k);
void L(int **p1, int *p2, int k, int n);

void ()
{
int a[5]={1, 2, 3, 4, 5};
DY(a, 4 , 5);
}

void DY(int *p, int k, int n)
{
int **p1;
int i, j, m;

j=C(n, k);

p1=(int **) malloc(j*sizeof(int *));

for (i=0; i<j; i++)
p1[i]=(int *) malloc(k*sizeof(int));

L(p1, p, k, n);

for (i=0; i<j; i++)
{
for (m=0; m<k; m++)
printf ("%d", *(p1[i]+m));
printf ("n");
}
}

int C(int n, int k)
{
if (k==0 || k==n)
return (1);
return (C(n-1, k)+C(n-1, k-1));
}

void L(int **p1, int *p2, int k, int n)
{
int i;
if (k==1)
{
for (i=0; i<n; i++)
*p1[i]=*(p2+i);
}
else
{
if (k==n)
{
for (i=0; i<n; i++)
*(p1[0]+i)=*(p2+i);
}
else
{
int j, c, d, z1, z2;
int **p;
j=0; d=1; c=1;
for (i=n-k; i>=0; i--)
{
p=(int **) malloc(c*sizeof(int *));

for (z1=0; z1<c; z1++)
p[z1]=(int *) malloc((k-1)*sizeof(int));

L(p, p2+i+1, k-1, n-i-1);

for (z1=0; z1<c; z1++)
for (z2=0; z2<(k-1); z2++)
*(p1[z1+j]+z2+1)=*(p[z1]+z2);

while (j<d)
{
*p1[j]=*(p2+i);
j++;
}

if (i!=0)
{
c=(c*(n-i))/(n-i-k+1);
d=d+c;
}
}
}
}
}