leetcode 1140. 石子游戏 II

本文探讨了在特定游戏场景中,如何运用深度优先搜索(DFS)与动态规划(DP)策略来求解亚历克斯与李之间的最优解。通过定义函数f(i,M),我们能够计算出在不同游戏状态下的最大收益,同时利用二维DP数组存储中间结果以减少重复计算,提高算法效率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目
在这里插入图片描述
思路

  • 想得到亚历克斯的最大值,那么李就要取最小值,考虑使用深度优先搜索遍历,定义函数:f(i,M)f\left ( i,M \right )f(i,M)表示piles从位置i开始到最后的以[1,2*M]为范围所能取到的最大值,使用公式

f(i,M)=sum(piles[i:])−min(f(i+x,max(m,i))),1≤x≤2∗Mf\left ( i,M \right )=sum\left ( piles\left [ i: \right ] \right )-min\left ( f\left ( i+x,max(m,i) \right )\right ),1\leq x\leq2*M f(i,M)=sum(piles[i:])min(f(i+x,max(m,i)))1x2M

  • 前者表示亚历克斯所能取到的最大值(当然实际不能取到,这表示从数组i开始后面所有的和),后者表示亚历克斯取完了以后,李能取到的最小值,两者相减为亚历克斯实际能取到的最大值。
  • 同时,为了节省计算,使用dp二维数组来存储 f(i,M) 的结果,行表示i,列表示M,如果有了相应的结果就使用相应的结果,如果没有则递归,并存入数组。

时间
在这里插入图片描述
代码

class Solution {
    private int n=0;
    private int[][] dp;
    public int stoneGameII(int[] piles) {
        n=piles.length;
        int[] s=new int[n];
        s[n-1]=piles[n-1];
        for(int i=n-2;i>=0;i--){
            s[i]=s[i+1]+piles[i];
        }
        dp=new int[2*n][2*n];
        return dfs(0,1,s);
    }
    public int dfs(int index,int M,int[] s){
        if(index>n){
            return 0;
        }else if(index+2*M>=n){
            return s[index];
        }else{
            int min=Integer.MAX_VALUE;
            for(int i=1;i<=2*M;i++){
                if(dp[index+i][Math.max(M,i)]!=0){
                    min=Math.min(min,dp[index+i][Math.max(M,i)]);
                }else{
                    int temp=dfs(index+i,Math.max(M,i),s);
                    min=Math.min(min,temp);
                    dp[index+i][Math.max(M,i)]=temp;
                }
                
            }
            return s[index]-min;
        }
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值