zoukankan      html  css  js  c++  java
  • b_lc_石子游戏 VII(区间dp套博弈)

    一排 n 块石子。每个回合,可从行中 移除 最左边的石头或最右边的石头,并获得与该行中剩余石头值之 和 相等的得分。当没有石头可移除时,得分较高者获胜。Bob总是输,Alice总是赢,所以Bob尽力 减小得分的差值,而爱丽丝最大限度地 扩大得分的差值。Alice先手,问比赛结束时的最大得分差值(即Alice赢的分数)

    思路:f[i][j]表示剩余stone[i,j]时的最大得分差值

    • 我取最左边的石子时,能拿到的分数是s[j]-s[i],因为后手也是聪明的,所以我能赢的分数就是s[j]-s[i]-f[i+1][j]
    • 我取最右边的石子时,能拿到的分数是s[j-1]-s[i-1],因为后手也是聪明的,所以我能赢的分数就是s[j-1]-s[i-1]-f[i][j-1]

    迭代写法

    class Solution:
        def stoneGameVII(self, A: List[int]) -> int:
            n=len(A)
            f,s=[[0]*(n+1) for i in range(n+1)], [0]*(n+1)
            for i in range(n):
                s[i+1]=s[i]+A[i]
    
            for l in range(2,n+1):
                for i in range(1,n-l+2): #i∈[1,n-l+1],比如n=5,l=2时,i=4,j=4+2-1
                    j=i+l-1
                    f[i][j]=max(s[j]-s[i]-f[i+1][j], s[j-1]-s[i-1]-f[i][j-1])
            return f[1][n]
    

    递归,慢一倍

    class Solution:
        def stoneGameVII(self, A: List[int]) -> int:
            def get(l,r):
                return s[r]-s[l]
            @cache
            def dfs(l,r):
                if l==r: return 0
                return max(get(l,r)-dfs(l+1,r), get(l-1,r-1)-dfs(l,r-1))
    
            n=len(A)
            s=[0]*(n+1)
            for i in range(n):
                s[i+1]=s[i]+A[i]
            ans=dfs(1,n)
            dfs.cache_clear()
            return ans
    
  • 相关阅读:
    spring 配置详解
    SpringBoot 快速整合Mybatis(去XML化+注解进阶)
    Spring Boot Mvc 单元测试
    Connect to DB2 database in eclipse via jdbc
    spring boot 学习
    小程序扫描普通链接二维码跳转小程序指定界面
    开启MySQL远程访问权限 允许远程连接
    JS概述
    全然用linux工作,放弃windows
    FarPoint.Win.Spread 常规操作
  • 原文地址:https://www.cnblogs.com/wdt1/p/14133823.html
Copyright © 2011-2022 走看看