题目大意:
有一种兑奖游戏,是从集合{1, 2,..., 49}中选6个数字作为兑奖号,一种策略就是现确定一个大小为k的子集(6 < k < 13),然后从中选取6个数字。
现有多个测例,每个测例都给出k(测例以k = 0结束),接着给出k个数字(从小到大排列),现要求输出k个数字中6个数字的全部组合,要求每种组合中的数字都是升序排列的,并且所有组合按照字典序升序排列,即前一个组合字典序小于后一个输出的组合,每个组合占一行,各个输出测例之间空出一行,最后一个测例后面不要空行。
注释代码:
/*
* Problem ID : POJ 2245 Lotto
* Author : Lirx.t.Una
* Language : C
* Run Time : 0 ms
* Run Memory : 156 KB
*/
#include <stdio.h>
//maximum k
//子集的最大容量
#define MAXK 13
//存放k个数字
//范围为1~49,处于char的范围内
char num[MAXK];
int
main() {
int iscn;
int n;//子集大小
int i;//计数变量
int a, b, c, d, e, f;//枚举技术变量
iscn = 0;
while ( scanf("%d", &n), n ) {
if ( iscn )//测例之间的空行
putchar('\n');
for ( i = 0; i < n; i++ )
scanf("%d", num + i);
//枚举,a < b < c < d < e < f的关系能保证组合中的数字一定是升序排列的
//并且都是从前往后枚举,所以各组合一定是字典序上升的
for ( a = 0; a < n - 5; a++ )
for ( b = a + 1; b < n - 4; b++ )
for ( c = b + 1; c < n - 3; c++ )
for ( d = c + 1; d < n - 2; d++ )
for ( e = d + 1; e < n - 1; e++ )
for ( f = e + 1; f < n; f++ )
printf("%d %d %d %d %d %d\n", num[a], num[b], num[c], num[d], num[e], num[f]);
iscn++;
}
return 0;
}
无注释代码:
#include <stdio.h>
#define MAXK 13
char num[MAXK];
int
main() {
int iscn;
int n;
int i;
int a, b, c, d, e, f;
iscn = 0;
while ( scanf("%d", &n), n ) {
if ( iscn )
putchar('\n');
for ( i = 0; i < n; i++ )
scanf("%d", num + i);
for ( a = 0; a < n - 5; a++ )
for ( b = a + 1; b < n - 4; b++ )
for ( c = b + 1; c < n - 3; c++ )
for ( d = c + 1; d < n - 2; d++ )
for ( e = d + 1; e < n - 1; e++ )
for ( f = e + 1; f < n; f++ )
printf("%d %d %d %d %d %d\n", num[a], num[b], num[c], num[d], num[e], num[f]);
iscn++;
}
return 0;
}
单词解释:
lotto:n, 兑奖游戏(多指卡片兑奖)
subset:n, 子集
demonstrate:vt, 证明,展示
Ulm:地名,乌尔姆,德国南部城市