Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit f5db36b

Browse files
feat: add solutions to lc problem: No.3573 (doocs#4468)
No.3573.Best Time to Buy and Sell Stock V
1 parent 078c02d commit f5db36b

File tree

7 files changed

+395
-8
lines changed

7 files changed

+395
-8
lines changed

‎solution/3500-3599/3573.Best Time to Buy and Sell Stock V/README.md‎

Lines changed: 145 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -82,32 +82,173 @@ edit_url: https://github.com/doocs/leetcode/edit/main/solution/3500-3599/3573.Be
8282

8383
<!-- solution:start -->
8484

85-
### 方法一
85+
### 方法一:动态规划
86+
87+
我们定义 $f[i][j][k]$ 表示在前 $i$ 天内,最多进行 $j$ 笔交易,且当前状态为 $k$ 时的最大利润。这里的状态 $k$ 有三种可能:
88+
89+
- 若 $k = 0,ドル表示当前没有持有股票。
90+
- 若 $k = 1,ドル表示当前持有一支股票。
91+
- 若 $k = 2,ドル表示当前持有一支股票的空头。
92+
93+
初始时,对任意 $j \in [1, k],ドル都有 $f[0][j][1] = -prices[0]$ 和 $f[0][j][2] = prices[0]$。这表示在第 0 天买入一支股票或卖出一支股票的空头。
94+
95+
接下来,我们可以通过状态转移来更新 $f[i][j][k]$ 的值。对于每一天 $i$ 和每笔交易 $j,ドル我们可以根据当前状态 $k$ 来决定如何更新:
96+
97+
- 若 $k = 0,ドル表示当前没有持有股票,这个状态可以由以下三种情况转移而来:
98+
- 前一天没有持有股票。
99+
- 前一天持有一支股票,并在今天卖出。
100+
- 前一天持有一支股票的空头,并在今天买回。
101+
- 若 $k = 1,ドル表示当前持有一支股票,这个状态可以由以下两种情况转移而来:
102+
- 前一天持有一支股票。
103+
- 前一天没有持有股票,并在今天买入。
104+
- 若 $k = 2,ドル表示当前持有一支股票的空头,这个状态可以由以下两种情况转移而来:
105+
- 前一天持有一支股票的空头。
106+
- 前一天没有持有股票,并在今天卖出。
107+
108+
即,对于 1ドル \leq i < n$ 和 1ドル \leq j \leq k,ドル我们有以下状态转移方程:
109+
110+
$$
111+
\begin{aligned}
112+
f[i][j][0] &= \max(f[i - 1][j][0], f[i - 1][j][1] + prices[i], f[i - 1][j][2] - prices[i]) \\
113+
f[i][j][1] &= \max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]) \\
114+
f[i][j][2] &= \max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i])
115+
\end{aligned}
116+
$$
117+
118+
最终,我们需要返回 $f[n - 1][k][0],ドル即在前 $n$ 天内,最多进行 $k$ 笔交易,且当前没有持有股票时的最大利润。
119+
120+
时间复杂度 $O(n \times k),ドル空间复杂度 $O(n \times k)$。其中 $n$ 为数组 $\textit{prices}$ 的长度,而 $k$ 为最大交易次数。
86121

87122
<!-- tabs:start -->
88123

89124
#### Python3
90125

91126
```python
92-
127+
class Solution:
128+
def maximumProfit(self, prices: List[int], k: int) -> int:
129+
n = len(prices)
130+
f = [[[0] * 3 for _ in range(k + 1)] for _ in range(n)]
131+
for j in range(1, k + 1):
132+
f[0][j][1] = -prices[0]
133+
f[0][j][2] = prices[0]
134+
for i in range(1, n):
135+
for j in range(1, k + 1):
136+
f[i][j][0] = max(
137+
f[i - 1][j][0],
138+
f[i - 1][j][1] + prices[i],
139+
f[i - 1][j][2] - prices[i],
140+
)
141+
f[i][j][1] = max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i])
142+
f[i][j][2] = max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i])
143+
return f[n - 1][k][0]
93144
```
94145

95146
#### Java
96147

97148
```java
98-
149+
class Solution {
150+
public long maximumProfit(int[] prices, int k) {
151+
int n = prices.length;
152+
long[][][] f = new long[n][k + 1][3];
153+
for (int j = 1; j <= k; ++j) {
154+
f[0][j][1] = -prices[0];
155+
f[0][j][2] = prices[0];
156+
}
157+
for (int i = 1; i < n; ++i) {
158+
for (int j = 1; j <= k; ++j) {
159+
f[i][j][0] = Math.max(f[i - 1][j][0],
160+
Math.max(f[i - 1][j][1] + prices[i], f[i - 1][j][2] - prices[i]));
161+
f[i][j][1] = Math.max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]);
162+
f[i][j][2] = Math.max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i]);
163+
}
164+
}
165+
return f[n - 1][k][0];
166+
}
167+
}
99168
```
100169

101170
#### C++
102171

103172
```cpp
104-
173+
class Solution {
174+
public:
175+
long long maximumProfit(vector<int>& prices, int k) {
176+
int n = prices.size();
177+
long long f[n][k + 1][3];
178+
memset(f, 0, sizeof(f));
179+
for (int j = 1; j <= k; ++j) {
180+
f[0][j][1] = -prices[0];
181+
f[0][j][2] = prices[0];
182+
}
183+
184+
for (int i = 1; i < n; ++i) {
185+
for (int j = 1; j <= k; ++j) {
186+
f[i][j][0] = max({f[i - 1][j][0], f[i - 1][j][1] + prices[i], f[i - 1][j][2] - prices[i]});
187+
f[i][j][1] = max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]);
188+
f[i][j][2] = max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i]);
189+
}
190+
}
191+
192+
return f[n - 1][k][0];
193+
}
194+
};
105195
```
106196

107197
#### Go
108198

109199
```go
200+
func maximumProfit(prices []int, k int) int64 {
201+
n := len(prices)
202+
f := make([][][3]int, n)
203+
for i := range f {
204+
f[i] = make([][3]int, k+1)
205+
}
206+
207+
for j := 1; j <= k; j++ {
208+
f[0][j][1] = -prices[0]
209+
f[0][j][2] = prices[0]
210+
}
211+
212+
for i := 1; i < n; i++ {
213+
for j := 1; j <= k; j++ {
214+
f[i][j][0] = max(f[i-1][j][0], f[i-1][j][1]+prices[i], f[i-1][j][2]-prices[i])
215+
f[i][j][1] = max(f[i-1][j][1], f[i-1][j-1][0]-prices[i])
216+
f[i][j][2] = max(f[i-1][j][2], f[i-1][j-1][0]+prices[i])
217+
}
218+
}
219+
220+
return int64(f[n-1][k][0])
221+
}
222+
```
110223

224+
#### TypeScript
225+
226+
```ts
227+
function maximumProfit(prices: number[], k: number): number {
228+
const n = prices.length;
229+
const f: number[][][] = Array.from({ length: n }, () =>
230+
Array.from({ length: k + 1 }, () => Array(3).fill(0)),
231+
);
232+
233+
for (let j = 1; j <= k; ++j) {
234+
f[0][j][1] = -prices[0];
235+
f[0][j][2] = prices[0];
236+
}
237+
238+
for (let i = 1; i < n; ++i) {
239+
for (let j = 1; j <= k; ++j) {
240+
f[i][j][0] = Math.max(
241+
f[i - 1][j][0],
242+
f[i - 1][j][1] + prices[i],
243+
f[i - 1][j][2] - prices[i],
244+
);
245+
f[i][j][1] = Math.max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]);
246+
f[i][j][2] = Math.max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i]);
247+
}
248+
}
249+
250+
return f[n - 1][k][0];
251+
}
111252
```
112253

113254
<!-- tabs:end -->

‎solution/3500-3599/3573.Best Time to Buy and Sell Stock V/README_EN.md‎

Lines changed: 145 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -80,32 +80,173 @@ We can make 36ドル of profit through 3 transactions:
8080

8181
<!-- solution:start -->
8282

83-
### Solution 1
83+
### Solution 1: Dynamic Programming
84+
85+
We define $f[i][j][k]$ to represent the maximum profit on the first $i$ days, with at most $j$ transactions, and the current state $k$. Here, the state $k$ has three possibilities:
86+
87+
- If $k = 0,ドル it means we do not hold any stock.
88+
- If $k = 1,ドル it means we are holding a stock.
89+
- If $k = 2,ドル it means we are holding a short position.
90+
91+
Initially, for any $j \in [1, k],ドル we have $f[0][j][1] = -prices[0]$ and $f[0][j][2] = prices[0]$. This means buying a stock or opening a short position on day 0.
92+
93+
Next, we update $f[i][j][k]$ using state transitions. For each day $i$ and each transaction $j,ドル we update according to the current state $k$:
94+
95+
- If $k = 0,ドル meaning no stock is held, this state can be reached from three situations:
96+
- No stock was held the previous day.
97+
- A stock was held the previous day and sold today.
98+
- A short position was held the previous day and bought back today.
99+
- If $k = 1,ドル meaning a stock is held, this state can be reached from two situations:
100+
- A stock was held the previous day.
101+
- No stock was held the previous day and a stock is bought today.
102+
- If $k = 2,ドル meaning a short position is held, this state can be reached from two situations:
103+
- A short position was held the previous day.
104+
- No stock was held the previous day and a short position is opened (sold) today.
105+
106+
That is, for 1ドル \leq i < n$ and 1ドル \leq j \leq k,ドル we have the following state transition equations:
107+
108+
$$
109+
\begin{aligned}
110+
f[i][j][0] &= \max(f[i - 1][j][0], f[i - 1][j][1] + prices[i], f[i - 1][j][2] - prices[i]) \\
111+
f[i][j][1] &= \max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]) \\
112+
f[i][j][2] &= \max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i])
113+
\end{aligned}
114+
$$
115+
116+
Finally, we return $f[n - 1][k][0],ドル which is the maximum profit after at most $k$ transactions and not holding any stock at the end of $n$ days.
117+
118+
The time complexity is $O(n \times k),ドル and the space complexity is $O(n \times k),ドル where $n$ is the length of the array $\textit{prices}$ and $k$ is the maximum number of transactions.
84119

85120
<!-- tabs:start -->
86121

87122
#### Python3
88123

89124
```python
90-
125+
class Solution:
126+
def maximumProfit(self, prices: List[int], k: int) -> int:
127+
n = len(prices)
128+
f = [[[0] * 3 for _ in range(k + 1)] for _ in range(n)]
129+
for j in range(1, k + 1):
130+
f[0][j][1] = -prices[0]
131+
f[0][j][2] = prices[0]
132+
for i in range(1, n):
133+
for j in range(1, k + 1):
134+
f[i][j][0] = max(
135+
f[i - 1][j][0],
136+
f[i - 1][j][1] + prices[i],
137+
f[i - 1][j][2] - prices[i],
138+
)
139+
f[i][j][1] = max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i])
140+
f[i][j][2] = max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i])
141+
return f[n - 1][k][0]
91142
```
92143

93144
#### Java
94145

95146
```java
96-
147+
class Solution {
148+
public long maximumProfit(int[] prices, int k) {
149+
int n = prices.length;
150+
long[][][] f = new long[n][k + 1][3];
151+
for (int j = 1; j <= k; ++j) {
152+
f[0][j][1] = -prices[0];
153+
f[0][j][2] = prices[0];
154+
}
155+
for (int i = 1; i < n; ++i) {
156+
for (int j = 1; j <= k; ++j) {
157+
f[i][j][0] = Math.max(f[i - 1][j][0],
158+
Math.max(f[i - 1][j][1] + prices[i], f[i - 1][j][2] - prices[i]));
159+
f[i][j][1] = Math.max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]);
160+
f[i][j][2] = Math.max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i]);
161+
}
162+
}
163+
return f[n - 1][k][0];
164+
}
165+
}
97166
```
98167

99168
#### C++
100169

101170
```cpp
102-
171+
class Solution {
172+
public:
173+
long long maximumProfit(vector<int>& prices, int k) {
174+
int n = prices.size();
175+
long long f[n][k + 1][3];
176+
memset(f, 0, sizeof(f));
177+
for (int j = 1; j <= k; ++j) {
178+
f[0][j][1] = -prices[0];
179+
f[0][j][2] = prices[0];
180+
}
181+
182+
for (int i = 1; i < n; ++i) {
183+
for (int j = 1; j <= k; ++j) {
184+
f[i][j][0] = max({f[i - 1][j][0], f[i - 1][j][1] + prices[i], f[i - 1][j][2] - prices[i]});
185+
f[i][j][1] = max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]);
186+
f[i][j][2] = max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i]);
187+
}
188+
}
189+
190+
return f[n - 1][k][0];
191+
}
192+
};
103193
```
104194

105195
#### Go
106196

107197
```go
198+
func maximumProfit(prices []int, k int) int64 {
199+
n := len(prices)
200+
f := make([][][3]int, n)
201+
for i := range f {
202+
f[i] = make([][3]int, k+1)
203+
}
204+
205+
for j := 1; j <= k; j++ {
206+
f[0][j][1] = -prices[0]
207+
f[0][j][2] = prices[0]
208+
}
209+
210+
for i := 1; i < n; i++ {
211+
for j := 1; j <= k; j++ {
212+
f[i][j][0] = max(f[i-1][j][0], f[i-1][j][1]+prices[i], f[i-1][j][2]-prices[i])
213+
f[i][j][1] = max(f[i-1][j][1], f[i-1][j-1][0]-prices[i])
214+
f[i][j][2] = max(f[i-1][j][2], f[i-1][j-1][0]+prices[i])
215+
}
216+
}
217+
218+
return int64(f[n-1][k][0])
219+
}
220+
```
108221

222+
#### TypeScript
223+
224+
```ts
225+
function maximumProfit(prices: number[], k: number): number {
226+
const n = prices.length;
227+
const f: number[][][] = Array.from({ length: n }, () =>
228+
Array.from({ length: k + 1 }, () => Array(3).fill(0)),
229+
);
230+
231+
for (let j = 1; j <= k; ++j) {
232+
f[0][j][1] = -prices[0];
233+
f[0][j][2] = prices[0];
234+
}
235+
236+
for (let i = 1; i < n; ++i) {
237+
for (let j = 1; j <= k; ++j) {
238+
f[i][j][0] = Math.max(
239+
f[i - 1][j][0],
240+
f[i - 1][j][1] + prices[i],
241+
f[i - 1][j][2] - prices[i],
242+
);
243+
f[i][j][1] = Math.max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]);
244+
f[i][j][2] = Math.max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i]);
245+
}
246+
}
247+
248+
return f[n - 1][k][0];
249+
}
109250
```
110251

111252
<!-- tabs:end -->
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
class Solution {
2+
public:
3+
long long maximumProfit(vector<int>& prices, int k) {
4+
int n = prices.size();
5+
long long f[n][k + 1][3];
6+
memset(f, 0, sizeof(f));
7+
for (int j = 1; j <= k; ++j) {
8+
f[0][j][1] = -prices[0];
9+
f[0][j][2] = prices[0];
10+
}
11+
12+
for (int i = 1; i < n; ++i) {
13+
for (int j = 1; j <= k; ++j) {
14+
f[i][j][0] = max({f[i - 1][j][0], f[i - 1][j][1] + prices[i], f[i - 1][j][2] - prices[i]});
15+
f[i][j][1] = max(f[i - 1][j][1], f[i - 1][j - 1][0] - prices[i]);
16+
f[i][j][2] = max(f[i - 1][j][2], f[i - 1][j - 1][0] + prices[i]);
17+
}
18+
}
19+
20+
return f[n - 1][k][0];
21+
}
22+
};

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /