알고리즘/Leetcode
LeetCode_1140.Stone Game II
꼼지락꼼지락
2020. 12. 18. 11:27
leetcode.com/problems/stone-game-ii/
Stone Game II - LeetCode
Level up your coding skills and quickly land a job. This is the best place to expand your knowledge and get prepared for your next interview.
leetcode.com
Solution1.
class Solution:
def stoneGameII(self, a: List[int]) -> int:
@lru_cache(maxsize=None)
def minimax(idx, M, isAlex):
if idx > len(piles) : return 0
if isAlex:
# Alice`s Turn : Alice가 가장 이득을 보는 선택 1~2M개의 돌무더기를 선택
return max([sum(piles[idx:idx+x]) + minimax(idx+x, max(M,x),False) for x in range(1, 2*M + 1)])
else:
# Bob`s Turn : Alice의 이득이 최소가 되느 1~2M개의 돌무더기를 선택
return min([minimax(idx+x, max(M,x), True) for x in range(1, 2*M+1)])
return minimax(0,1,True)
Solution 2.
class Solution:
def stoneGameII(self, piles: List[int]) -> int:
n = len(piles)
@lru_cache(None)
def minimax(start_idx, M):
if n - start_idx <= 2 * M:
# 남은 돌을 모두 가져갈수 있다면
return sum(piles[start_idx:])
max_score = 0
all_sum = sum(piles[start_idx:])
for X in range(1, 2 * M + 1):
# Bob이 최소 이득을 보는 경우를 선택 -> maximize(all_sum - bob`s profit)
score = all_sum - minimax(start_idx + X, max(M, X))
max_score = max(max_score, score)
return max_score
return minimax(0, 1)
Solution 2-1. suffix_sum을 통해 구간합을 구하지 않도록 개선
class Solution:
def stoneGameII(self, piles: List[int]) -> int:
# suffix_sum
n = len(piles)
suffix_sum = [0 for _ in range(n)]
for i in range(n - 1, -1, -1):
suffix_sum[i] = (suffix_sum[i + 1] if i + 1 < n else 0) + piles[i]
@lru_cache(None)
def minimax(start_idx, M):
if n - start_idx <= 2 * M:
return suffix_sum[start_idx] # sum(piles[start_idx:])
max_score = 0
all_sum = suffix_sum[start_idx] # sum(piles[start_idx:])
for X in range(1, 2 * M + 1):
score = all_sum - minimax(start_idx + X, max(M, X))
max_score = max(max_score, score)
return max_score
return minimax(0, 1)
※ suffix_sum array : 끝에서부터 배열을 누적 시키거나, 배열의 누적합을 뒤집어서 생성. 특정 idx부터 배열 끝까지의 합을 바로바로 사용할수 있음
nums = [1,2,3,4,5]
n = len(nums)
suffix_sum = [0 for _ in range(n)]
# [0,0,0,0,0]
for i in range(n - 1, -1, -1):
suffix_sum[i] = (suffix_sum[i + 1] if i + 1 < n else 0) + piles[i]
# suffix_sum = [15,14,12,9,5]
# suffix_sum[0] -> 배열의 0 번째부터 배열 끝까지의 합, 1+2+3+4+5=15
# suffix_sum[3] -> 배열의 3 번째부터 배열 끝까지의 합, 4+5=9