编程语言
首页 > 编程语言> > 算法——石子游戏(区间DP,博弈)

算法——石子游戏(区间DP,博弈)

作者:互联网

简介

石子游戏其实就是多人博弈,如何求最优结果。它存在很多变种,比如不同的取石方式,不同的计算输赢的方式,在这里做一个汇总。

只能从两端取

石子游戏中,爱丽丝和鲍勃轮流进行自己的回合,爱丽丝先开始 。
有 n 块石子排成一排。每个玩家的回合中,可以从行中 移除 最左边的石头或最右边的石头,并获得与该行中剩余石头值之 和 相等的得分。当没有石头可移除时,得分较高者获胜。
鲍勃发现他总是输掉游戏(可怜的鲍勃,他总是输),所以他决定尽力 减小得分的差值 。爱丽丝的目标是最大限度地 扩大得分的差值 。
给你一个整数数组 stones ,其中 stones[i] 表示 从左边开始 的第 i 个石头的值,如果爱丽丝和鲍勃都 发挥出最佳水平 ,请返回他们 得分的差值 。
leetcode

解题思路:

class Solution {
    public int stoneGameVII(int[] w) {
        int n = w.length;
        int[] s = new int[n + 1];
        // 为了在O1的时间内获取两点之间的和,这里先去前缀和
        for(int i = 1;  i <= n; i++) s[i] = s[i - 1] + w[i - 1];
        // 状态表示数组
        int[][] f = new int[n + 1][n + 1];

		// 先枚举区间长度
        for(int len = 2; len <= n; len++) {
        	// 再枚举起点
            for(int i = 1; i + len - 1 <= n; i++) {
            	// 终点
                int j = i + len - 1;
                // 状态转移,取左端点或者又端点的最大值
                f[i][j] = Math.max(s[j] - s[i] - f[i + 1][j], s[j - 1] - s[i - 1] - f[i][j -1]);
            }
        }

        return f[1][n];
    }
}

标签:得分,鲍勃,int,石子,算法,差值,爱丽丝,DP
来源: https://blog.csdn.net/qq_36263268/article/details/111111449