We are playing the Guessing Game. The game will work as follows:
1
and n
.x
, you will pay x
dollars. If you run out of money, you lose the game.Given a particular n
, return the minimum amount of money you need to guarantee a win regardless of what number I pick.
For example:
If n = 10
, a possible winning strategy is as follows:
[1,10]
. Guess 7.
[8,10]
. Guess 9.
[1,6]
. Guess 3.
[4,6]
. Guess 5.
[1,2]
. Guess 1.
The worst case in all these scenarios is that you pay $16. Hence, you only need $16 to guarantee a win.
Can you implement an algorithm that finds the minimum amount of money needed to guarantee a win for any given n
?
We are playing a game where you have to guess a number I've picked between 1 and n
. If you guess wrong, I tell you if my number is higher or lower, and you pay an amount equal to your guess. The goal is to determine the minimum amount of money you need to guarantee a win, regardless of the number I pick.
A brute-force approach involves trying every possible guess at each step and recursively calculating the worst-case cost for each choice. This will have overlapping subproblems, so we'll show the dynamic programming approach next.
We can use dynamic programming to solve this problem efficiently. Let dp[i][j]
represent the minimum amount of money needed to guarantee a win when the range of possible numbers is from i
to j
(inclusive).
dp[i][i] = 0
(If there's only one number, you can guess it directly without any cost).[i, j]
, we can iterate through all possible guesses k
from i
to j
. For each k
, the worst-case cost would be k + max(dp[i][k-1], dp[k+1][j])
. We take the minimum of these worst-case costs for all k
to find dp[i][j]
.dp[i][j] = min(k + max(dp[i][k-1], dp[k+1][j])) for k in range(i, j + 1)
def getMoneyAmount(n):
dp = [[0] * (n + 1) for _ in range(n + 1)]
for length in range(2, n + 1):
for i in range(1, n - length + 2):
j = i + length - 1
dp[i][j] = float('inf')
for k in range(i, j + 1):
dp[i][j] = min(dp[i][j], k + max(dp[i][k - 1] if k > i else 0, dp[k + 1][j] if k < j else 0))
return dp[1][n]
As shown in example 1, to guarantee a win for n = 10
, the minimum amount of money needed is 16.
The algorithm calculates the dp
table by considering all subranges:
[1, 2]
, [2, 3]
, ..., [9, 10]
[1, 3]
, [2, 4]
, ..., [8, 10]
[1, 10]
For each range, it tries all possible guesses and uses the recursive relation mentioned to find the minimum cost.
n = 1
: The result is 0 because you can guess the number directly.n = 2
: The result is 1. Guess 1. If it's wrong, the number is 2 and you pay 1.dp
table (O(n^2)), and an inner loop for calculating the minimum cost for each cell (O(n)).dp
table of size n x n
.