目录
问题描述
某工作队接到一项任务,要求在A、B、C、D、E、F 6个队员中尽可能多地挑若干人,但有一下限制条件:
A和B两人中至少去一人;
A和D不能一起去;
A、E和F 3人中要派两人去。
B和C都去或都不去;
C和D两人中去一个;
若D不去,则E也不去。
问:应当让哪几个人去?
问题分析
问题类型
这是个选人问题,只存在两种情况,人选上了,人没选上。所以我们用0、1来表示是否选上(贴合0为假,非零为真)。
限制条件的表述
A和B两人中至少去一人
A、B之间必去一人,所以(a+b)>=1
(a + b) >= 1
A和D不能一起去
可以单去A,也可以单去D,还可以A、D都不去,唯独不能都去,也就是(a+d)!=2
(a + d) != 2
A、E和F 3人中要派两人去
三个人当中要有两个人去,也就是(a+e+f)=2
(a + e + f) == 2
B和C都去或都不去
这里有两种情况,一是都去(b+c)=2,二是都不去(b+c)=0.
((b + c) == 2 || (b + c) == 0)
C和D两人中去一个
两个之前去一个,代表只有一个1.
(c + d) == 1
若D不去,则E也不去
这里有三种可行情况,一是D去了,E没去。二是D、E都去了。三是D、E都没去。唯独不能出现D没去,E去了,也就是E=1,D=0。那么我们只要限制不可行的情况即可,(e-d)不等于1
(e - d) != 1
整段代码
思路
我们定义六个整型变量,用来表示六个队员。再定义一个数组,用来存放选上的人。定义count,用来将选上的人按顺序放在数组的空位置上。
利用多层for循环来实现穷举
将限制条件放入if语句中,用来判断这次的名单是不是符合要求。
打印每一种符合要求的情况。
代码
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
int main()
{
//表示六个队员
int a, b, c, d, e, f;
//参选名单
char arr[6] = { 0 };
//作为下标使用
int count = 0;
//穷举每一种情况,1代表去,0代表不去。
for (a = 0; a < 2; a++)
{
for (b = 0; b < 2; b++)
{
for (c = 0; c < 2; c++)
{
for (d = 0; d < 2; d++)
{
for (e = 0; e < 2; e++)
{
for(f=0;f<2;f++)
{
//找出符合要求的情况
if ((a + b) >= 1 && (a + d) != 2 && (a + e + f) == 2 && ((b + c) == 2 || (b + c) == 0) && (c + d) == 1 && (e - d) != 1)
{
//如果a=0,则没去,表示假,去了就是1,表示真
if (a)
{
arr[count] = 'A';
count++;
}
if (b)
{
arr[count] = 'B';
count++;
}
if (c)
{
arr[count] = 'C';
count++;
}
if (d)
{
arr[count] = 'D';
count++;
}
if (e)
{
arr[count] = 'E';
count++;
}
if (f)
{
arr[count] = 'F';
count++;
}
//将每种情况打印
for (int i = 0; i < 6 && arr[i] != 0; i++)
{
printf("%c ", arr[i]);
}
printf("\n");
//排除上一次情况对下一次情况的干扰
count = 0;
}
}
}
}
}
}
}
return 0;
}