Algorithms first

买卖股票的最佳时机 IV · 交互式算法学习

最多完成 k 笔交易,求最大利润。

#188 · 多维动态规划

买卖股票的最佳时机 IV

Best Time to Buy and Sell Stock IV

测试用例k = 2, prices = [2,4,1]
状态表3 个关键状态
步骤 1每个交易编号维护 buy/sell。k=2
010
2
4
1
1
当前状态转移来源
推荐

交易状态滚动数组

时间 O(nk)空间 O(k)

buy[j]、sell[j] 分别保存第 j 笔买入和卖出后的最大现金。

1function maxProfit(k, p) {2  if (k >= p.length / 2) return p.slice(1).reduce((s, x, i) => s + Math.max(0, x - p[i]), 0);3  const buy = Array(k + 1).fill(-Infinity),4    sell = Array(k + 1).fill(0);5  for (const x of p)6    for (let j = 1; j <= k; j++) {7      buy[j] = Math.max(buy[j], sell[j - 1] - x);8      sell[j] = Math.max(sell[j], buy[j] + x)9    }10  return sell[k];11}
多语言参考

Java · C++ · Go

来源 · CC BY-SA 4.0 ↗

这是一组同题正确实现,独立于上方当前动画方法;不同语言可能采用另一种正确策略。

1class Solution {2    private Integer[][][] f;3    private int[] prices;4    private int n;5 6    public int maxProfit(int k, int[] prices) {7        n = prices.length;8        this.prices = prices;9        f = new Integer[n][k + 1][2];10        return dfs(0, k, 0);11    }12 13    private int dfs(int i, int j, int k) {14        if (i >= n) {15            return 0;16        }17        if (f[i][j][k] != null) {18            return f[i][j][k];19        }20        int ans = dfs(i + 1, j, k);21        if (k > 0) {22            ans = Math.max(ans, prices[i] + dfs(i + 1, j, 0));23        } else if (j > 0) {24            ans = Math.max(ans, -prices[i] + dfs(i + 1, j - 1, 1));25        }26        return f[i][j][k] = ans;27    }28}
交互式算法学习

从执行步骤真正理解 LeetCode 经典 150

本站整理 150 道高频算法面试题和 302 种解法。动画方法同步展示 JavaScript 与 Python;每题另提供 Java、C++ 与 Go 同题参考实现。

多形态可视化数组、矩阵、DP 表、递归树、树图、链表、栈队列堆、区间和状态机按解法选择。
动画与代码同步当前状态、步骤说明、变量和代码高亮保持一一对应,可逐步播放和回退。
适合面试复习每种方案都给出思路、时间复杂度、空间复杂度、测试用例和 LeetCode 中文原题入口。
AlgoViz Lab

买卖股票的最佳时机 IV · 解法对比

最多完成 k 笔交易,求最大利润。

测试用例
k = 2, prices = [2,4,1]
题目分类
多维动态规划
解法对比
2
方案 1

按天×交易数二维 DP

dp[day][j][hold] 记录第 day 天完成至多 j 笔交易的最大现金。

时间
O(nk)
空间
O(nk)
方案 2

交易状态滚动数组

buy[j]、sell[j] 分别保存第 j 笔买入和卖出后的最大现金。

时间
O(nk)
空间
O(k)