当前位置:   article > 正文

蓝桥杯 算法训练 24点(Python)_python 24点

python 24点

资源限制

内存限制:256.0MB   C/C++时间限制:1.0s   Java时间限制:3.0s   Python时间限制:5.0s

问题描述

  24点游戏是一个非常有意思的游戏,很流行,玩法很简单:给你4张牌,每张牌上有数字(其中A代表1,J代表11,Q代表12,K代表13),你可以利用数学中的加、减、乘、除以及括号想办法得到24,例如:
  ((A*K)-J)*Q等价于((1*13)-11)*12=24
  加减乘不用多说了,但除法必须满足能整除才能除!这样有一些是得不到24点的,所以这里只要求求出不超过24的最大值。

输入格式

  输入第一行N(1<=N<=5)表示有N组测试数据。每组测试数据输入4行,每行一个整数(1到13)表示牌值。

输出格式

  每组测试数据输出一个整数,表示所能得到的最大的不超过24的值。

样例输入

3
3
3
3
3
1
1
1
1
12
5
13
1

样例输出

24
4
21

有两种思路,系统提交得分都是100分

方案一:

这个是我的思路,因为数据范围不大,所以我选择的是一步一步处理,首先将每一组数据的4个数顺序打乱,再分配三个可重复的运算符号,再加上不同的括号,依次计算,求出不大于24的最大值,如果遇到24,则提前结束当前组处理。

  1. from itertools import *
  2. n = int(input())
  3. nums = []
  4. strs = ['+', '-', '*', '/']
  5. # 将输入的数字4个一组,存到nums里
  6. for i in range(n):
  7. a = int(input())
  8. b = int(input())
  9. c = int(input())
  10. d = int(input())
  11. nums.append([a, b, c, d])
  12. # print(nums)
  13. for i in nums:
  14. nums1 = []
  15. ans = []
  16. flag = 1
  17. # 将四个数字顺序打乱
  18. for j in permutations(i):
  19. if list(j) not in nums1:
  20. nums1.append(list(j))
  21. # print(nums1)
  22. for j in nums1:
  23. # 每一种数字顺序,取出任意三个计算符号,符号可以重复
  24. for str1 in product(strs, repeat=3):
  25. a = j[0]
  26. b = j[1]
  27. c = j[2]
  28. d = j[3]
  29. # 共有11种加括号的方式,全部列举出来
  30. for num in range(11):
  31. formula = []
  32. if num == 0:
  33. formula = ['(', a, str1[0], b, ')', str1[1], c, str1[2], d]
  34. elif num == 1:
  35. formula = [a, str1[0], '(', b, str1[1], c, ')', str1[2], d]
  36. elif num == 2:
  37. formula = [a, str1[0], b, str1[1], '(', c, str1[2], d, ')']
  38. elif num == 3:
  39. formula = ['(', a, str1[0], b, str1[1], c, ')', str1[2], d]
  40. elif num == 4:
  41. formula = [a, str1[0], '(', b, str1[1], c, str1[2], d, ')']
  42. elif num == 5:
  43. formula = ['(', a, str1[0], b, ')', str1[1], '(', c, str1[2], d, ')']
  44. elif num == 6:
  45. formula = ['(', '(', a, str1[0], b, ')', str1[1], c, ')', str1[2], d]
  46. elif num == 7:
  47. formula = ['(', a, str1[0], '(', b, str1[1], c, ')', ')', str1[2], d]
  48. elif num == 8:
  49. formula = [a, str1[0], '(', '(', b, str1[1], c, ')', str1[2], d, ')']
  50. elif num == 9:
  51. formula = [a, str1[0], '(', b, str1[1], '(', c, str1[2], d, ')', ')']
  52. elif num == 10:
  53. formula = [a, str1[0], b, str1[1], c, str1[2], d]
  54. # 将最后的式子变成字符串
  55. strend = ''
  56. for m in formula:
  57. strend += str(m)
  58. try:
  59. # 计算字符串的值
  60. if eval(strend) % 1 == 0:
  61. ans_num = int(eval(strend))
  62. else:
  63. continue
  64. # 除0处理
  65. except ZeroDivisionError:
  66. continue
  67. if ans_num < 24: # 小于24的结果存到数组中,最后取最大值
  68. ans.append(ans_num)
  69. elif ans_num == 24: # 如果是24,提前结束本组数据的处理
  70. print('24')
  71. flag = 0
  72. break
  73. if flag == 0:
  74. break
  75. if flag == 0:
  76. break
  77. if flag == 0:
  78. continue
  79. print(max(ans))

方案二:

此方案是做完之后在网上找的代码,然后稍作修改,删掉了部分多余的代码得到的,整体思路就是利用深度优先(DFS)遍历,每次进行两个数的运算,计算结果替换掉原来的两个数,直到只剩一个数,然后计算结束继续回溯,直到计算出所有不大于24的结果,取最大值,同样,遇到24提前返回。

  1. n = int(input())
  2. nums = [[] for i in range(n)]
  3. for i in range(n * 4):
  4. nums[i // 4].append(int(input()))
  5. def dfs(arr):
  6. global res, flag, sto # res为计算结果;flag标记计算结果是否为24;sto用于储存小于24的计算结果
  7. if flag == 1: # flag==1说明找到最终结果了
  8. return
  9. if len(arr) == 1: # 递归出口
  10. res = arr[0]
  11. if res == 24:
  12. flag = 1
  13. sto = [24] # 当计算结果为24时,直接令sto=[24]
  14. return
  15. elif res > 24: # 计算结果大于24的不要
  16. return
  17. else:
  18. sto.add(res) # 计算结果小于24的加入集合中,最后取集合最大值得到最终结果
  19. return
  20. for i in range(len(arr)):
  21. a = arr[i]
  22. arr2 = arr.copy() # 作用与回溯相同,用了arr2就不需要回溯了
  23. arr2.pop(i)
  24. for j in range(len(arr2)):
  25. b = arr2[j]
  26. arr2.pop(j)
  27. # 下面4个部分分别是加减乘除,删除a,b后插入c,然后回溯,回溯完成后退回到这里继续执行下面的计算
  28. c = a + b
  29. arr2.insert(j, c)
  30. dfs(arr2)
  31. arr2.pop(j)
  32. c = a - b
  33. arr2.insert(j, c)
  34. dfs(arr2)
  35. arr2.pop(j)
  36. c = a * b
  37. arr2.insert(j, c)
  38. dfs(arr2)
  39. arr2.pop(j)
  40. arr2.insert(j, b)
  41. if b != 0 and a % b == 0: # 除数不为0,并且能整除
  42. c = a // b
  43. arr2.pop(j)
  44. arr2.insert(j, c)
  45. dfs(arr2)
  46. arr2.pop(j)
  47. arr2.insert(j, b)
  48. for arrs in nums:
  49. sto = set([])
  50. flag = 0
  51. res = 0
  52. dfs(arrs)
  53. print(max(sto))

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/你好赵伟/article/detail/64306
推荐阅读
相关标签
  

闽ICP备14008679号