枚举:
概念:
枚举就是简单地将每种情况给列举出来,再对列举出来的所有情况进行判断,枚举又被称为大暴力,这个形容形象生动,简单的枚举确实很暴力。
例子:火柴棍模型:
题目描述:现在有n根火柴棍,需要用n根火柴棍拼出A+B=C这样的等式,0需6根、1需2根、2需5根、3需5根、4需4根、5需5根、6需6根、7需3根、8需7根、9需6根,等号’=‘和’+'各需2根。题目给定:
1:最多24根火柴棍;
2:A、B、C都是整数;
3:火柴棍必须用完。
分析一波:因为火柴棍组成数字中有相同火柴棍组成不同数字的,所以单一对火柴棍的数量枚举是不行的,比如现在枚举出来火柴棍是5根,那它是代表数字2还是5呢?所以这种方法行不通,我们换种思路:对这些可能出现的数字范围进行枚举,题目给定最多24根火柴棍,那除去‘+’和‘=’共4根火柴棍,那还剩下20根火柴棍用于三个数字的变化。根据火柴棍组出的数字可以看出,数字1所需火柴棍最少,只需2根,那最大数肯定都是由1组成的数。20根火柴棍最多组成10组1,10组1分成3个数字,按平均每个数字111,可以组成111 + 111 = 1111这样的等式,现在A和B变化的范围都很大,那数字111肯定不是最大值。再让数字分成1111,先让B和C是1111,那多余的两根火柴棍放在A的位置,组成11+1111=1111这样的式子,等式并不相等,多了11,但也接近相等了,继续往上走,如果取5个1组成数字11111,只能组成11111=11111的式子,A无法取值,根据分析,等式中的数最大只能取到1111,那对它进行遍历。
#include<stdio.h>
int fun(int x)
{
int sum = 0;
int s[11] = {6, 2, 5, 5, 4, 5, 6, 3, 7, 6}; //数组来储存每个数字需要用到的火柴棍根数
while(x/10 != 0) //当这个数是非一位数时
{
sum = sum + s[x % 10];
x = x / 10;
}
sum = sum + s[x];
return sum;
}
int main()
{
int x, num = 0;
int a, b, c;
scanf("%d", &x); //输入火柴棍根数
for(a = 0; a <= 1111; a++)
{
for(b = 0; b <= 1111; b++)
{
c = a + b;
if(fun(a) + fun(b) + fun(c) == x - 4)
{
printf("%d+%d=%d\n", a, b, c);
num++;
}
}
}
printf("能构成%d个等式\n", num);
getchar(); getchar();
return 0;
}