题解 | 24点游戏算法

24点游戏算法

https://www.nowcoder.com/practice/fbc417f314f745b1978fc751a54ac8cb

import sys

arr = list(map(int, input().split()))

N = 4
visit = []
st = []
path = []
def dfs(l, res):
    # if len(path)==4:
        # if path[0][0] == 0 and path[1][0]==1 and path[2][0]==2 or path[3][0]==3:
        #     print(path)
    if l==4 and (abs(res - 24) < 1e-4):
        # print(path, res)
        return True
    # 特殊处理情况:剩下两个数乘除运算后于当前相加减,或者剩下两个数加减后于当前相乘除情况
    if l==2:
        num_remain = [arr[i] for i in range(N) if not visit[i]]
        wait_res1 = [num_remain[0] * num_remain[1], num_remain[1] / num_remain[0], num_remain[0] / num_remain[1]]
        wait_res2 = [num_remain[0] + num_remain[1], num_remain[0] - num_remain[1], num_remain[1] - num_remain[0]]
        for w in wait_res1:
            if abs(res + w - 24)<1E-5 or abs(res - w - 24)<1E-5 or abs(-res + w - 24)<1E-5:
                return True
        for w in wait_res2:
            if abs(res * w - 24)<1E-5 or (w !=0 and abs(res / w - 24)<1E-5) or (res!=0 and abs(w/res - 24)<1E-5):
                return True


    # 此处循环未包含剩下两个数乘除运算后于当前相加减情况,或者剩下两个数加减后于当前相乘除情况
    for i in range(N):
        if not visit[i]:
            visit[i] = True
            
            path.append((i, res + arr[i]))
            if dfs(l+1, res + arr[i]):
                return True
            path.pop()
            path.append((i, res - arr[i]))
            if dfs(l+1, res - arr[i]):
                return True
            path.pop()
            path.append((i, arr[i] - res))
            if dfs(l+1, arr[i] - res):
                return True
            path.pop()
            path.append((i, res * arr[i]))
            if dfs(l+1, res * arr[i]):
                return True
            path.pop()
            if arr[i]!=0:
                path.append((i, res / arr[i]))
                if dfs(l+1, res / arr[i]):
                    return True
                path.pop()
            if res !=0:
                path.append((i, arr[i] / res))
                if dfs(l+1, arr[i] / res):
                    return True
                path.pop()
            visit[i] = False
    return False
for i in range(N):
    # 各个元素作为起始点
    visit = [False for _ in range(N)]
    path=[(i, arr[i])]
    visit[i] = True
    if dfs(1, arr[i]):
        print("true")
        exit(0)

print("false")

如果不在代码中交换已求和部分和剩余未求和部分的顺序,对于4个元素的情况,DFS会漏掉前两个和后两个元素各自计算的结果再次运算。因此我在代码中手动加入了这个特殊情形。看到有些代码样例将求和的结果和未运算的结果放在一起用于dfs下一步的数组,这种方法可以应对任意长度的数组,而不受限于4个元素的情况。

全部评论

相关推荐

背景&nbsp;双一流本硕&nbsp;双非大圆满&nbsp;只找游戏开发相关的岗位。&nbsp;8&nbsp;月初开始秋招到现在&nbsp;投了四五十家吧,&nbsp;目前两&nbsp;offer,&nbsp;不打算继续投了,把剩下的流程走完就开始沉淀了。目前两&nbsp;offer&nbsp;一个是网易互娱测开&nbsp;base&nbsp;广州,一个是江娱互动客户端开发&nbsp;base&nbsp;北京。应该确定网易这个了,说实话北京这个我挺想去的,这家的产品和工作氛围我了解了也不错,是那种踏实做事的,可惜我是广东人。网易的测开是调剂的二志愿,看了下有内部转岗机会,所以打算后面找个时间提前实习,沉淀下再做一个&nbsp;demo&nbsp;作品,写一些&nbsp;shader,增强下图形学渲染的能力,再学点编辑器开发。看到时候内部转岗或者春招继续投客户端开发这样。后面还能再动摇的话应该就灵犀或者腾子了吧(假如这两家确认的是客户端开发岗的话)。-----------------------补下timeline网易互娱&nbsp;测开&nbsp;8.2笔试&nbsp;&nbsp;8.21&nbsp;技术面&nbsp;&nbsp;8.29&nbsp;leader&amp;HRBP面(终面)&nbsp;9.8&nbsp;录用审核(之前一直显示面试中)9.14&nbsp;oc江娱互动&nbsp;客户端开发&nbsp;8.29主程面&nbsp;9.3&nbsp;制作人面&nbsp;9.5&nbsp;BOSS面&nbsp;9.11&nbsp;口头OC&nbsp;9.15&nbsp;正式offer后面考虑了一下&nbsp;&nbsp;感觉还是能走开发就开发吧,测开不太感兴趣,要内部活水转岗还要满1年才能申请。。
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务