Leetcode---1406. 石子游戲 III---博弈問題(動態規劃)

1406. 石子游戲 III

Alice 和 Bob 用幾堆石子在做遊戲。幾堆石子排成一行,每堆石子都對應一個得分,由數組 stoneValue 給出。

Alice 和 Bob 輪流取石子,Alice 總是先開始。在每個玩家的回合中,該玩家可以拿走剩下石子中的的前 1、2 或 3 堆石子 。比賽一直持續到所有石頭都被拿走。

每個玩家的最終得分爲他所拿到的每堆石子的對應得分之和。每個玩家的初始分數都是 0 。比賽的目標是決出最高分,得分最高的選手將會贏得比賽,比賽也可能會出現平局。

假設 Alice 和 Bob 都採取 最優策略 。如果 Alice 贏了就返回 “Alice” ,Bob 贏了就返回 “Bob”,平局(分數相同)返回 “Tie” 。

示例 1:

輸入:values = [1,2,3,7]
輸出:"Bob"
解釋:Alice 總是會輸,她的最佳選擇是拿走前三堆,得分變成 6 。但是 Bob 的得分爲 7,Bob 獲勝。

示例 2:

輸入:values = [1,2,3,-9]
輸出:"Alice"
解釋:Alice 要想獲勝就必須在第一個回合拿走前三堆石子,給 Bob 留下負分。
如果 Alice 只拿走第一堆,那麼她的得分爲 1,接下來 Bob 拿走第二、三堆,得分爲 5 。之後 Alice 只能拿到分數 -9 的石子堆,輸掉比賽。
如果 Alice 拿走前兩堆,那麼她的得分爲 3,接下來 Bob 拿走第三堆,得分爲 3 。之後 Alice 只能拿到分數 -9 的石子堆,同樣會輸掉比賽。
注意,他們都應該採取 最優策略 ,所以在這裏 Alice 將選擇能夠使她獲勝的方案。

示例 3:

輸入:values = [1,2,3,6]
輸出:"Tie"
解釋:Alice 無法贏得比賽。如果她決定選擇前三堆,她可以以平局結束比賽,否則她就會輸。

示例 4:

輸入:values = [1,2,3,-1,-2,-3,7]
輸出:"Alice"

示例 5:

輸入:values = [-1,-2,-3]
輸出:"Tie"

提示:

  • 1 <= values.length <= 50000
  • -1000 <= values[i] <= 1000

實現代碼

class Solution {
public:
    string stoneGameIII(vector<int>& stoneValue) {
        int len = stoneValue.size(), sum = 0, inf = 1 << 31;
        vector<int> dp(len + 3, 0);
        for (int i = len - 1; i >= 0; i--) {
            sum += stoneValue[i], dp[i] = inf;
            // 排除後面3個(只選當前), 排除最後面2個(只選當前和後一個), 排除最後面1個(選當前和後兩個)
            for (int j = 1; j  <= 3; j++) dp[i] = max(dp[i], sum - dp[i + j]);
        }
        if(sum < (dp[0] * 2) ) return "Alice";
        if (sum == (dp[0] * 2)) return "Tie";
        return "Bob";
    }
};
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章