算法描述而下(来自组合数学):
从r-组合a1a2...ar=1234....r开始。
当a1a2...ar!=(n-r+1)(n-r+2)...n时,做
(1)确定最大的整数K,使ak+1<=n且ak+1不是a1,a2,a3,...,ar.
(2)用r-组合
a1...ak-1(ak+1)(ak+2)...(ak+r-k+1)
替换a1a2...ar.
代码:
#include <stdio.h>
#define N 7//集合中有N个数
#define M 5//任意取M个数出来
int a[N] ;
int b[M] ;
void init(){//初始化这两个数组
int i ;
for(i=0 ;i < N ; i++){
a[i] = i + 1 ;
}
for(i=0 ; i < M ; i++){
b[i] = a[i] ;
}
}
int check(int t){//判断t是否在b数组中
int i = 0 ;
while( (i<M) && (b[i] != t) ) i++ ;
if(i == M) return 1 ;//表示元素不是集合中
else return 0 ;//表于元素在集合中
}
int getK(){//得到满足一定条件的k,这样的条件ak+1<=n,而且ak不在b数组中的,最大的那个k
int max = a[N-1] ;//取最大的数
int i ;
int t ;
for(i=M-1 ; i>=0 ; --i){
t = b[i] + 1 ;
if(t <= max && check(t) && (b[i]+M-i)<=max){
return i ;
}
}
return -1 ;
}
int replace(){//用新的数去代替旧的数据
int k = getK() ;
if(k == -1) return -1 ;
int c = b[k];
for(;k<M; k++) {
b[k] = c + 1 ;
++c ;
}
return 1 ;
}
void show(){
int i ;
for(i = 0 ; i<M; i++){
printf("%d ",b[i]) ;
}
printf("\n") ;
}
int main(){
int count = 1 ;
init() ;
while(1){
show() ;
if(replace() == -1) {
break ;
}
++count ;
}
printf("count = %d",count) ;
return 0;
}
运行结果: