mirror of
https://github.com/youngyangyang04/leetcode-master.git
synced 2025-07-06 23:28:29 +08:00
Merge branch 'master' into master
This commit is contained in:
@ -404,6 +404,47 @@ func max188(a, b int) int {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
版本三:空间优化版本
|
||||||
|
|
||||||
|
```go
|
||||||
|
func maxProfit(k int, prices []int) int {
|
||||||
|
n := len(prices)
|
||||||
|
// k次交易,2 * k种状态
|
||||||
|
// 状态从1开始计算,避免判断
|
||||||
|
// 奇数时持有(保持或买入)
|
||||||
|
// 偶数时不持有(保持或卖出)
|
||||||
|
dp := make([][]int, 2)
|
||||||
|
dp[0] = make([]int, k * 2 + 1)
|
||||||
|
dp[1] = make([]int, k * 2 + 1)
|
||||||
|
|
||||||
|
// 奇数状态时持有,i += 2
|
||||||
|
for i := 1; i <= k * 2; i += 2 {
|
||||||
|
dp[0][i] = -prices[0]
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 1; i < len(prices); i++ {
|
||||||
|
for j := 1; j <= k * 2; j++ {
|
||||||
|
if j % 2 == 1 {
|
||||||
|
dp[i % 2][j] = max(dp[(i - 1) % 2][j], dp[(i - 1) % 2][j - 1] - prices[i])
|
||||||
|
} else {
|
||||||
|
dp[i % 2][j] = max(dp[(i - 1) % 2][j], dp[(i - 1) % 2][j - 1] + prices[i])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return dp[(n - 1) % 2][k * 2]
|
||||||
|
}
|
||||||
|
|
||||||
|
func max(a, b int) int {
|
||||||
|
if a > b {
|
||||||
|
return a
|
||||||
|
}
|
||||||
|
return b
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
### JavaScript:
|
### JavaScript:
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
@ -558,3 +599,4 @@ impl Solution {
|
|||||||
<a href="https://programmercarl.com/other/kstar.html" target="_blank">
|
<a href="https://programmercarl.com/other/kstar.html" target="_blank">
|
||||||
<img src="../pics/网站星球宣传海报.jpg" width="1000"/>
|
<img src="../pics/网站星球宣传海报.jpg" width="1000"/>
|
||||||
</a>
|
</a>
|
||||||
|
|
||||||
|
@ -357,6 +357,42 @@ func max(a, b int) int {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
```go
|
||||||
|
// 一维优化版本
|
||||||
|
// 时间复杂度O(n), 空间复杂度O(1)
|
||||||
|
func maxProfit(prices []int) int {
|
||||||
|
|
||||||
|
// 0: 持有,一直持有和买入
|
||||||
|
// 1: 不持有,一直不持有(不包含前一天卖出,因为这样的一天是冷静期,状态有区别)
|
||||||
|
// 2:不持有,今天卖出
|
||||||
|
// 3:冷静期,前一天卖出(一直不持有)
|
||||||
|
dp0, dp1, dp2, dp3 := -prices[0], 0, 0, 0
|
||||||
|
|
||||||
|
n := len(prices)
|
||||||
|
|
||||||
|
for i := 1; i < n; i++ {
|
||||||
|
t0 := max(dp0, max(dp1, dp3)-prices[i])
|
||||||
|
t1 := max(dp1, dp3)
|
||||||
|
t2 := dp0 + prices[i]
|
||||||
|
t3 := dp2
|
||||||
|
|
||||||
|
// 更新
|
||||||
|
dp0, dp1, dp2, dp3 = t0, t1, t2, t3
|
||||||
|
}
|
||||||
|
|
||||||
|
return max(dp1, max(dp2, dp3))
|
||||||
|
}
|
||||||
|
|
||||||
|
func max(a, b int) int {
|
||||||
|
if a > b {
|
||||||
|
return a
|
||||||
|
}
|
||||||
|
return b
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
### Javascript:
|
### Javascript:
|
||||||
|
|
||||||
> 不同的状态定义 感觉更容易理解些
|
> 不同的状态定义 感觉更容易理解些
|
||||||
@ -540,3 +576,4 @@ impl Solution {
|
|||||||
<a href="https://programmercarl.com/other/kstar.html" target="_blank">
|
<a href="https://programmercarl.com/other/kstar.html" target="_blank">
|
||||||
<img src="../pics/网站星球宣传海报.jpg" width="1000"/>
|
<img src="../pics/网站星球宣传海报.jpg" width="1000"/>
|
||||||
</a>
|
</a>
|
||||||
|
|
||||||
|
@ -168,6 +168,7 @@ class Solution {
|
|||||||
```
|
```
|
||||||
|
|
||||||
### Python:
|
### Python:
|
||||||
|
> 版本一:
|
||||||
|
|
||||||
```python
|
```python
|
||||||
class Solution:
|
class Solution:
|
||||||
@ -181,6 +182,34 @@ class Solution:
|
|||||||
stack.append(i%len(nums))
|
stack.append(i%len(nums))
|
||||||
return dp
|
return dp
|
||||||
```
|
```
|
||||||
|
|
||||||
|
> 版本二:针对版本一的优化
|
||||||
|
|
||||||
|
```python3
|
||||||
|
class Solution:
|
||||||
|
def nextGreaterElements(self, nums: List[int]) -> List[int]:
|
||||||
|
res = [-1] * len(nums)
|
||||||
|
stack = []
|
||||||
|
#第一次遍历nums
|
||||||
|
for i, num in enumerate(nums):
|
||||||
|
while stack and num > nums[stack[-1]]:
|
||||||
|
res[stack[-1]] = num
|
||||||
|
stack.pop()
|
||||||
|
stack.append(i)
|
||||||
|
#此时stack仍有剩余,有部分数‘无下一个更大元素’待修正
|
||||||
|
#第二次遍历nums
|
||||||
|
for num in nums:
|
||||||
|
#一旦stack为空,就表明所有数都有下一个更大元素,可以返回结果
|
||||||
|
if not stack:
|
||||||
|
return res
|
||||||
|
while stack and num > nums[stack[-1]]:
|
||||||
|
res[stack[-1]] = num
|
||||||
|
stack.pop()
|
||||||
|
#不要将已经有下一个更大元素的数加入栈,这样会重复赋值,只需对第一次遍历剩余的数再尝试寻找下一个更大元素即可
|
||||||
|
#最后仍有部分最大数无法有下一个更大元素,返回结果
|
||||||
|
return res
|
||||||
|
```
|
||||||
|
|
||||||
### Go:
|
### Go:
|
||||||
|
|
||||||
```go
|
```go
|
||||||
@ -203,7 +232,6 @@ func nextGreaterElements(nums []int) []int {
|
|||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### JavaScript:
|
### JavaScript:
|
||||||
|
|
||||||
```JS
|
```JS
|
||||||
|
@ -283,32 +283,10 @@ class Solution:
|
|||||||
return TreeNode(val)
|
return TreeNode(val)
|
||||||
self.traversal(root, val)
|
self.traversal(root, val)
|
||||||
return root
|
return root
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
递归法(版本二)
|
递归法(版本二)
|
||||||
```python
|
```python
|
||||||
class Solution:
|
|
||||||
def insertIntoBST(self, root, val):
|
|
||||||
if root is None:
|
|
||||||
return TreeNode(val)
|
|
||||||
parent = None
|
|
||||||
cur = root
|
|
||||||
while cur:
|
|
||||||
parent = cur
|
|
||||||
if val < cur.val:
|
|
||||||
cur = cur.left
|
|
||||||
else:
|
|
||||||
cur = cur.right
|
|
||||||
if val < parent.val:
|
|
||||||
parent.left = TreeNode(val)
|
|
||||||
else:
|
|
||||||
parent.right = TreeNode(val)
|
|
||||||
return root
|
|
||||||
```
|
|
||||||
|
|
||||||
递归法(版本三)
|
|
||||||
```python
|
|
||||||
class Solution:
|
class Solution:
|
||||||
def insertIntoBST(self, root: Optional[TreeNode], val: int) -> Optional[TreeNode]:
|
def insertIntoBST(self, root: Optional[TreeNode], val: int) -> Optional[TreeNode]:
|
||||||
if root is None or root.val == val:
|
if root is None or root.val == val:
|
||||||
@ -326,7 +304,7 @@ class Solution:
|
|||||||
return root
|
return root
|
||||||
```
|
```
|
||||||
|
|
||||||
递归法(版本四)
|
递归法(版本三)
|
||||||
```python
|
```python
|
||||||
class Solution:
|
class Solution:
|
||||||
def insertIntoBST(self, root, val):
|
def insertIntoBST(self, root, val):
|
||||||
@ -340,10 +318,9 @@ class Solution:
|
|||||||
root.right = self.insertIntoBST(root.right, val)
|
root.right = self.insertIntoBST(root.right, val)
|
||||||
|
|
||||||
return root
|
return root
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
迭代法
|
迭代法(版本一)
|
||||||
```python
|
```python
|
||||||
class Solution:
|
class Solution:
|
||||||
def insertIntoBST(self, root, val):
|
def insertIntoBST(self, root, val):
|
||||||
@ -366,10 +343,53 @@ class Solution:
|
|||||||
else:
|
else:
|
||||||
parent.right = node # 将新节点连接到父节点的右子树
|
parent.right = node # 将新节点连接到父节点的右子树
|
||||||
|
|
||||||
return root
|
return root
|
||||||
|
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
|
迭代法(版本二)
|
||||||
|
```python
|
||||||
|
class Solution:
|
||||||
|
def insertIntoBST(self, root, val):
|
||||||
|
if root is None:
|
||||||
|
return TreeNode(val)
|
||||||
|
parent = None
|
||||||
|
cur = root
|
||||||
|
while cur:
|
||||||
|
parent = cur
|
||||||
|
if val < cur.val:
|
||||||
|
cur = cur.left
|
||||||
|
else:
|
||||||
|
cur = cur.right
|
||||||
|
if val < parent.val:
|
||||||
|
parent.left = TreeNode(val)
|
||||||
|
else:
|
||||||
|
parent.right = TreeNode(val)
|
||||||
|
return root
|
||||||
|
```
|
||||||
|
|
||||||
|
迭代法(精简)
|
||||||
|
```python
|
||||||
|
class Solution:
|
||||||
|
def insertIntoBST(self, root: Optional[TreeNode], val: int) -> Optional[TreeNode]:
|
||||||
|
if not root: # 如果根节点为空,创建新节点作为根节点并返回
|
||||||
|
return TreeNode(val)
|
||||||
|
cur = root
|
||||||
|
while cur:
|
||||||
|
if val < cur.val:
|
||||||
|
if not cur.left: # 如果此时父节点的左子树为空
|
||||||
|
cur.left = TreeNode(val) # 将新节点连接到父节点的左子树
|
||||||
|
return root
|
||||||
|
else:
|
||||||
|
cur = cur.left
|
||||||
|
elif val > cur.val:
|
||||||
|
if not cur.right: # 如果此时父节点的左子树为空
|
||||||
|
cur.right = TreeNode(val) # 将新节点连接到父节点的右子树
|
||||||
|
return root
|
||||||
|
else:
|
||||||
|
cur = cur.right
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
-----
|
-----
|
||||||
### Go
|
### Go
|
||||||
|
|
||||||
|
@ -188,6 +188,20 @@ class Solution:
|
|||||||
return max(dp[-1][0], dp[-1][1])
|
return max(dp[-1][0], dp[-1][1])
|
||||||
```
|
```
|
||||||
|
|
||||||
|
```python
|
||||||
|
class Solution:
|
||||||
|
def maxProfit(self, prices: List[int], fee: int) -> int:
|
||||||
|
# 持有股票手上的最大現金
|
||||||
|
hold = -prices[0] - fee
|
||||||
|
# 不持有股票手上的最大現金
|
||||||
|
not_hold = 0
|
||||||
|
for price in prices[1:]:
|
||||||
|
new_hold = max(hold, not_hold - price - fee)
|
||||||
|
new_not_hold = max(not_hold, hold + price)
|
||||||
|
hold, not_hold = new_hold, new_not_hold
|
||||||
|
return not_hold
|
||||||
|
```
|
||||||
|
|
||||||
### Go:
|
### Go:
|
||||||
|
|
||||||
```go
|
```go
|
||||||
|
@ -388,3 +388,85 @@ if __name__ == "__main__":
|
|||||||
main()
|
main()
|
||||||
|
|
||||||
```
|
```
|
||||||
|
### C
|
||||||
|
|
||||||
|
前缀和
|
||||||
|
```c
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
int n = 0, m = 0, ret_ver = 0, ret_hor = 0;
|
||||||
|
|
||||||
|
// 读取行和列的值
|
||||||
|
scanf("%d%d", &n, &m);
|
||||||
|
// 动态分配数组a(横)和b(纵)的空间
|
||||||
|
int *a = (int *)malloc(sizeof(int) * n);
|
||||||
|
int *b = (int *)malloc(sizeof(int) * m);
|
||||||
|
|
||||||
|
// 初始化数组a和b
|
||||||
|
for (int i = 0; i < n; i++)
|
||||||
|
{
|
||||||
|
a[i] = 0;
|
||||||
|
}
|
||||||
|
for (int i = 0; i < m; i++)
|
||||||
|
{
|
||||||
|
b[i] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 读取区块权值并计算每行和每列的总权值
|
||||||
|
for (int i = 0; i < n; i++)
|
||||||
|
{
|
||||||
|
for (int j = 0; j < m; j++)
|
||||||
|
{
|
||||||
|
int tmp;
|
||||||
|
scanf("%d", &tmp);
|
||||||
|
a[i] += tmp;
|
||||||
|
b[j] += tmp;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 计算每列以及每行的前缀和
|
||||||
|
for (int i = 1; i < n; i++)
|
||||||
|
{
|
||||||
|
a[i] += a[i - 1];
|
||||||
|
}
|
||||||
|
for (int i = 1; i < m; i++)
|
||||||
|
{
|
||||||
|
b[i] += b[i - 1];
|
||||||
|
}
|
||||||
|
|
||||||
|
// 初始化ret_ver和ret_hor为最大可能值
|
||||||
|
ret_hor = a[n - 1];
|
||||||
|
ret_ver = b[m - 1];
|
||||||
|
|
||||||
|
// 计算按行划分的最小差异
|
||||||
|
int ret2 = 0;
|
||||||
|
while (ret2 < n)
|
||||||
|
{
|
||||||
|
ret_hor = (ret_hor > abs(a[n - 1] - 2 * a[ret2])) ? abs(a[n - 1] - 2 * a[ret2]) : ret_hor;
|
||||||
|
// 原理同列,但更高级
|
||||||
|
ret2++;
|
||||||
|
}
|
||||||
|
// 计算按列划分的最小差异
|
||||||
|
int ret1 = 0;
|
||||||
|
while (ret1 < m)
|
||||||
|
{
|
||||||
|
if (ret_ver > abs(b[m - 1] - 2 * b[ret1]))
|
||||||
|
{
|
||||||
|
ret_ver = abs(b[m - 1] - 2 * b[ret1]);
|
||||||
|
}
|
||||||
|
ret1++;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 输出最小差异
|
||||||
|
printf("%d\n", (ret_ver <= ret_hor) ? ret_ver : ret_hor);
|
||||||
|
|
||||||
|
// 释放分配的内存
|
||||||
|
free(a);
|
||||||
|
free(b);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
```
|
||||||
|
@ -264,6 +264,7 @@ if __name__ == "__main__":
|
|||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### JavaScript
|
### JavaScript
|
||||||
|
|
||||||
``` JavaScript
|
``` JavaScript
|
||||||
@ -312,3 +313,47 @@ function prefixSum() {
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
### C
|
||||||
|
|
||||||
|
```C
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
int main(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
int num;
|
||||||
|
// 读取数组长度
|
||||||
|
scanf("%d", &num);
|
||||||
|
|
||||||
|
// 使用动态内存分配而不是静态数组,以适应不同的输入大小
|
||||||
|
int *a = (int *)malloc((num + 1) * sizeof(int));
|
||||||
|
|
||||||
|
// 初始化前缀和数组的第一个元素为0
|
||||||
|
a[0] = 0;
|
||||||
|
|
||||||
|
// 读取数组元素并计算前缀和
|
||||||
|
for (int i = 1; i <= num; i++)
|
||||||
|
{
|
||||||
|
int mm;
|
||||||
|
scanf("%d", &mm);
|
||||||
|
// 累加前缀和
|
||||||
|
a[i] = a[i - 1] + mm;
|
||||||
|
}
|
||||||
|
|
||||||
|
int m, n;
|
||||||
|
// 循环读取区间并计算区间和,直到输入结束
|
||||||
|
// scanf()返回成功匹配和赋值的个数,到达文件末尾则返回 EOF
|
||||||
|
while (scanf("%d%d", &m, &n) == 2)
|
||||||
|
{
|
||||||
|
// 输出区间和,注意区间是左闭右开,因此a[n+1]是包含n的元素的前缀和
|
||||||
|
printf("%d\n", a[n+1] - a[m]);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 释放之前分配的内存
|
||||||
|
free(a);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user