多语言展示
当前在线:1605今日阅读:27今日分享:41

怎么用“枚举法”解决24点问题?

24点问题,是一个比较有趣的游戏。比如:给定五个数字——5,6,3,8,9,要求用这五个数的任意排列,配合加、减、乘、除,使得结果等于24。下面,我用Mathematica来寻找可能存在的等式。
工具/原料
1

电脑

2

Mathematica

初步
1

给定五个数字:A={5,6,3,8,9}

2

准备四个运算符号。注意,运算符号可以重复。

3

用B和A的后四个元素,可以做成一个二维列表:{B, A[[2 ;; 5]]}这是一个形式上的2*4的矩阵,尽管里面的元素不是数字。

4

转置一下,就得到4*2的形式矩阵:{B, A[[2 ;; 5]]} // Transpose;展开为一维列表,可以发现,运算符号和数字是交错排列的:{B, A[[2 ;; 5]]} // Transpose//Flatten

5

在开头加上A的第一个元素,就得到一个“算式”:{A[[1]], {B, A[[2 ;; 5]]} // Transpose} // Flatten只不过被“逗号”隔开了。

6

看看,StringJoin能不能把上面的“算式”串起来?——:{A[[1]], {B, A[[2 ;; 5]]} // Transpose} // Flatten // StringJoin结果会报错,提示“算式”里面的数字,不是字符串的形式。

7

需要把“算式”里面的所有元素,全部转化为字符串的形式,然后才能串起来:ToString[#] & /@ ({A[[1]], {B, A[[2 ;; 5]]} // Transpose} //     Flatten) // StringJoin得到的式子,还是一个字符串的形式,不是真正意义上的算式。

8

如果需要计算这个式子,需要转化为表达式:% // ToExpression结果是85/18≠24,所以,这个式子,不是我们要寻找的算式。

枚举法
1

A里面的数字,可以有若干不同的排列方法:b = Permutations[A];

2

运算符号允许重复出现:a = Tuples[{'+', '-', '*', '/'}, 4];

3

用b里面的每一种排列方法,配套a里面的某个运算法则,就得到很多表达式;用if语句判断,如果表达式等于24,就保留字符串形式的算式,否则写为0;用Union把重复的式子(主要是0)去掉;把0(一般会位于开头)去掉。

注意事项

这个方法有一个缺点,就是重复的算式比较多。

推荐信息