为了促进各部门员工的交流,百度举办了一场全公司范围内的“拳皇”(百度内部最流行的格斗游戏)友谊赛,负责组织这场比赛的是百度的超级“拳皇”迷W.Z。W.Z不想用传统的淘汰赛或者循环赛的方式,而是自己制定了一个比赛规则。
由于一些员工(比如同部门或者相邻部门员工)平时接触的机会比较多,为了促进不同部门之间的交流,W.Z希望员工自由分组。不同组之间的每两个人都会进行一场友谊赛而同一组内的人之间不会打任何比赛。
比如4个人,编号为1~4,如果分为两个组并且1,2一个组,3,4一个组,那么一共需要打四场比赛:1 vs 3,1 vs 4,2 vs 3,2 vs 4。而如果是1,2,3一组,4单独一组,那么一共需要打三场比赛: 1 vs 4,2 vs 4,3 vs 4。
很快W.Z意识到,这样的比赛规则可能会让比赛的场数非常多。W.Z想知道如果有N个人,通过上面这种比赛规则,总比赛场数有可能为K场吗?比如3个人,如果只分到一组则不需要比赛,如果分到两组则需要2场比赛,如果分为三组则需要3场比赛。但是无论怎么分都不可能恰需要1场比赛。
相信作为编程高手的你一定知道该怎么回答这个问题了吧?那么现在请你帮助W.Z吧。
输入要求:
每行为一组数据,包含两个数字 N, K(0<N<=500, K>=0)。例:
2 0
2 1
3 1
3 2
输出要求:
对输入的N,K 如果N个员工通过一定的分组方式可以使比赛场数恰好为K,则输出"YES",否则输出"NO"(请全部使用大写字母),每组数据占一行。例:
YES
YES
NO
YES
代码如下:
1 #include<stdio.h> 2 #include<conio.h> 3 int result[500]; 4 int status[1000]={0}; 5 int sum(int *a, int len) 6 { 7 int sum = 0, i, j; 8 for (i = 0; i < len; ++i) { 9 for(j = i + 1; j < len; ++j) { 10 sum += a[i] * a[j]; 11 } 12 } 13 return sum; 14 } 15 void split(int n, int k, int c) 16 { 17 if (k == 0) return; 18 if (n == k) 19 {
21 result[c]=k; 22 status[sum(result,c+1)]=1; 23 if (k == 1)return; 24 } 25 int i = k; 26 for (;i >= 1; i--) 27 { 28 result[c] = i; 29 split(n - i, i < n - i ? i : n - i, c + 1); 30 } 31 } 32 33 int main() 34 { 35 int n,k; 36 scanf("%d %d",&n,&k); 37 if(n<1||n>500||k<0) 38 return 0; 39 split(n, n - 1, 0); 40 if(!k||status[k])printf("YES!\n"); 41 else printf("NO!\n"); 42 getch(); 43 return 0; 44 }