Taro Logo

Stone Game III

Medium
1 views
2 months ago

Alice and Bob are playing a game with stones arranged in a row. Each stone has an associated integer value given in the stoneValue array. Alice and Bob take turns, with Alice starting first. On each turn, a player can take 1, 2, or 3 stones from the beginning of the row. The score of each player is the sum of the values of the stones taken, starting from 0. The objective is to have the highest score at the end. Assume both players play optimally.

Return "Alice" if Alice will win, "Bob" if Bob will win, or "Tie" if they end with the same score.

Example 1: Input: stoneValue = [1,2,3,7] Output: "Bob"

Example 2: Input: stoneValue = [1,2,3,-9] Output: "Alice"

Example 3: Input: stoneValue = [1,2,3,6] Output: "Tie"

Explain your code and provide a big O analysis for both space and time complexity.

Sample Answer
def stoneGameIII(stoneValue):
    n = len(stoneValue)
    dp = {}

    def solve(i):
        if i >= n:
            return 0
        if i in dp:
            return dp[i]

        ans = float('-inf')
        curr_sum = 0
        for x in range(1, min(4, n - i + 1)):
            curr_sum += stoneValue[i + x - 1]
            ans = max(ans, curr_sum - solve(i + x))

        dp[i] = ans
        return ans

    result = solve(0)
    if result > 0:
        return "Alice"
    elif result < 0:
        return "Bob"
    else:
        return "Tie"

Explanation:

This code implements a dynamic programming solution to determine the winner of the stone game. The solve(i) function calculates the maximum score Alice can achieve starting from index i. The dp dictionary is used for memoization to avoid redundant calculations.

  • If solve(0) is positive, Alice wins.
  • If solve(0) is negative, Bob wins.
  • If solve(0) is zero, it's a tie.

Example Walkthrough:

For stoneValue = [1, 2, 3, 7], the function calculates the best move for Alice at each step, assuming both players play optimally. Alice tries taking 1, 2, or 3 stones and recursively calculates the score difference. The memoization ensures efficiency.

For stoneValue = [1, 2, 3, -9], Alice would take the first three stones to maximize her score and leave Bob with a negative score.

For stoneValue = [1, 2, 3, 6], the function evaluates all possible moves for Alice, determining the outcome as a tie.

Big O Analysis:

Time Complexity:

The time complexity is O(n) because each position in the stoneValue array is visited only once due to memoization.

Space Complexity:

The space complexity is O(n) due to the dp dictionary, which stores the results for each position in the array.

Edge Cases:

  • Empty array: The code handles this case gracefully as the loop condition min(4, n - i + 1) will result in no iteration, returning 0.
  • All negative values: Alice will choose the move that minimizes Bob's score, which might result in Bob winning.
  • All positive values: Both players will try to maximize their scores, potentially leading to a tie.