Leetcode 2029. 石子游戏 IX
生活随笔
收集整理的這篇文章主要介紹了
Leetcode 2029. 石子游戏 IX
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
Alice 和 Bob 再次設計了一款新的石子游戲。現有一行 n 個石子,每個石子都有一個關聯的數字表示它的價值。給你一個整數數組?stones?,其中?stones[i]?是第?i?個石子的價值。
Alice 和 Bob 輪流進行自己的回合,Alice?先手。每一回合,玩家需要從?stones?中移除任一石子。
- 如果玩家移除石子后,導致?所有已移除石子?的價值?總和?可以被 3 整除,那么該玩家就?輸掉游戲?。
- 如果不滿足上一條,且移除后沒有任何剩余的石子,那么 Bob 將會直接獲勝(即便是在 Alice 的回合)。
假設兩位玩家均采用?最佳?決策。如果 Alice 獲勝,返回?true?;如果 Bob 獲勝,返回?false?。
示例 1:
輸入:stones = [2,1] 輸出:true 解釋:游戲進行如下: - 回合 1:Alice 可以移除任意一個石子。 - 回合 2:Bob 移除剩下的石子。 已移除的石子的值總和為 1 + 2 = 3 且可以被 3 整除。因此,Bob 輸,Alice 獲勝。示例 2:
輸入:stones = [2] 輸出:false 解釋:Alice 會移除唯一一個石子,已移除石子的值總和為 2 。 由于所有石子都已移除,且值總和無法被 3 整除,Bob 獲勝。示例 3:
輸入:stones = [5,1,2,4,3] 輸出:false 解釋:Bob 總會獲勝。其中一種可能的游戲進行方式如下: - 回合 1:Alice 可以移除值為 1 的第 2 個石子。已移除石子值總和為 1 。 - 回合 2:Bob 可以移除值為 3 的第 5 個石子。已移除石子值總和為 = 1 + 3 = 4 。 - 回合 3:Alices 可以移除值為 4 的第 4 個石子。已移除石子值總和為 = 1 + 3 + 4 = 8 。 - 回合 4:Bob 可以移除值為 2 的第 3 個石子。已移除石子值總和為 = 1 + 3 + 4 + 2 = 10. - 回合 5:Alice 可以移除值為 5 的第 1 個石子。已移除石子值總和為 = 1 + 3 + 4 + 2 + 5 = 15. Alice 輸掉游戲,因為已移除石子值總和(15)可以被 3 整除,Bob 獲勝。提示:
- 1 <= stones.length <= 105
- 1 <= stones[i] <= 104
解法:
一開始以為需要狀態壓縮,結果看過數據范圍就放棄了,最后寫了個dfs+記憶化(死馬當活馬醫),超時了。在比賽快結束的時候才想到將數據預處理為0,1,2;但后續處理還是沒想出來。看了題解,然后按自己的理解,寫了一個由許多if-else的解法。
class Solution {bool check(int s0, int s1, int s2){bool flag = true;if (s1 == 0) //當s1為0時{if (s2 >= 3) //當大于3時,{flag = false; //3個s2必能被3整除if ((s0 & 1) == 1) //s0為奇數時才能改變結果flag = true;return flag;}else //s2=1,2都是Bob贏{return false;}}else{s1 -= 1; //先手選s1int num = min(s1, s2);s1 -= num, s2 -= num;//后面必定是s1與s2的循環,如當s1為1的個數,1121212...12if (s2 != 0) //去掉循環后,剩下s2{flag=true; //B取S2,則A贏if ((s0 & 1) == 1) //當0的個數為奇數個,才能改變flag = false;return flag;}else //剩下s1{if (s1 <= 1) //不論誰取光,都是Bob贏return false; else if (s1 >= 2)//最開始的s1,再加上兩個s1,必能被整除(3%3,6%3){flag = false; //A取完,就能被整除了if ((s0 & 1) == 1)// 當0的個數為奇數個,才能改變flag = true;return flag;}}}return flag; //不會到這里,這里要是不寫,leetcod}public:bool stoneGameIX(vector<int>& stones) {int s0 = 0, s1 = 0, s2 = 0;for (auto &stone : stones){if (stone % 3 == 0)++s0;else if (stone % 3 == 1)++s1;else++s2;}if (s1 == 0 && s2 == 0)return false;return check(s0, s1, s2) || check(s0, s2, s1); //先手選擇1,或者0} };看別人的題解總結一下,讓自己下次遇到能快速寫出來:由check()代碼中可以看出Alice要贏只有三種情況:
1.S0為奇數:(1)s1==0,s2>=3(2)s1>s2+2,這兩種可以整合為s1>s2+2
2.S0為偶數:s2>=s1
那么從整體代碼中看即為
bool stoneGameIX(vector<int>& stones) {int s0 = 0, s1 = 0, s2 = 0;for (auto &stone : stones){if (stone % 3 == 0)++s0;else if (stone % 3 == 1)++s1;else++s2;}if((s0&1)==0)return s1!=0&&s2!=0;else return s1>s2+2||s2>s1+2;}總結
以上是生活随笔為你收集整理的Leetcode 2029. 石子游戏 IX的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: echarts实现颜色渐变
- 下一篇: 使用N2N软件远程管理DLAP221设备