[Best Time to Buy and Sell Stock] Problem Set
Leetcode Dynamic Programming Problem Set (3)
- 121.Best Time to Buy and Sell Stock
- 122.Best Time to Buy and Sell Stock II
- 123.Best Time to Buy and Sell Stock III
- 188.Best Time to Buy and Sell Stock IV
- 309.Best Time to Buy and Sell Stock with Cooldown
- 714.Best Time to Buy and Sell Stock with Transaction Fee
There are 3 options in each trade day: buy, sell, hold
We can use a 3d array to log all situations:dp[i][k][1 or 0]
= the maximum profit at the end of the i-th day with at most k transactions and with 0 or 1 stock in our hand AFTER taking the action
1 | # either always haven't got stock, or sold a stock. |
1 | # Base case:dp[-1] means before day 0, haven't start yet. |
121. Best Time to Buy and Sell Stock
k = 1.1
2
3
4
5
6
7
8
9
10def maxProfit(self, prices: List[int]) -> int:
if len(prices) < 2:
return 0
buy = prices[0]
profit = 0
for i in range(1, len(prices)):
buy = min(prices[i], buy)
profit = max(profit, prices[i] - buy)
return profit
122. Best Time to Buy and Sell Stock II
k = inf1
2
3
4
5
6
7
8
9def maxProfit(self, prices: List[int]) -> int:
last_buy = -prices[0] # have one stock, either bought or kept
last_sell = 0 # have no stock, either sold or kept
for i in range(1, len(prices)):
cur_buy = max(last_buy, last_sell - prices[i])
cur_sell = max(last_sell, last_buy+ prices[i])
last_buy = cur_buy
last_sell = cur_sell
return last_sell
123. Best Time to Buy and Sell Stock III
k = 21
2
3
4
5
6
7
8
9
10def maxProfit(self, prices: List[int]) -> int:
# last_k_numberOfStock
gain_1_1, gain_2_1 = float('-inf'), float('-inf')
gain_1_0, gain_2_0 = 0, 0
for p in prices:
gain_2_0 = max(gain_2_0, gain_2_1 + p)
gain_2_1 = max(gain_2_1, gain_1_0 - p)
gain_1_0 = max(gain_1_0, gain_1_1 + p)
gain_1_1 = max(gain_1_1, -p)
return gain_2_0
188. Best Time to Buy and Sell Stock IV
k = inf
The most general case. Very hard to understand1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16class Solution:
def maxProfit(self, k: int, prices: List[int]) -> int:
if len(prices) < 2 or not k:
return 0
n = len(prices)
k = min(k, n // 2)
stock0 = [0] * (k + 1)
stock1 = [float('-inf')] * (k + 1)
for price in prices:
for j in range(k, 0, -1):
stock0[j] = max(stock0[j], stock1[j] + price)
stock1[j] = max(stock1[j], stock0[j-1] - price)
return stock0[k]
309. Best Time to Buy and Sell Stock with Cooldown
k = inf + cooldown1
2
3
4
5
6
7
8
9
10
11
12
13
14
15def maxProfit(self, prices: List[int]) -> int:
if len(prices) < 2:
return 0
buy = float('-inf')
sell = 0
prev_sell = 0
for p in prices:
temp = sell
sell = max(sell, buy + p)
buy = max(buy, prev_sell - p)
prev_sell = temp
return sell
714. Best Time to Buy and Sell Stock with Transaction Fee
The same as Best Time to Buy and Sell Stock II, just need to deduct fee from profit.1
2
3
4
5
6
7
8
9
10
11
12def maxProfit(self, prices: List[int], fee: int) -> int:
if len(prices) < 2:
return 0
buy = float('-inf')
sell = 0
for p in prices:
sell = max(sell, buy + p - fee)
buy = max(buy, sell - p)
return sell