返回

LeetCode 《初级算法》动态规划之买卖股票的最佳时机

前端

导言

对于渴望在金融市场中获得丰厚回报的投资者来说,把握买卖股票的最佳时机至关重要。LeetCode《初级算法》中提供的动态规划问题“买卖股票的最佳时机”正是为了测试程序员解决此类问题的技能。在本文中,我们将使用JavaScript来实现这个问题,深入探索动态规划的精髓,并提供清晰易懂的解题思路和代码实现。

问题

给定一个数组,其中每个元素表示某天股票的价格。设计一个算法,计算出在该数组中买卖股票可以获得的最大利润。你可以多次买卖股票,但必须在卖出之前买入股票。

解题思路

动态规划是一种自顶向下解决问题的技术,特别适用于需要计算多个子问题的优化问题。在这个问题中,我们可以将问题分解为一系列子问题:

  • 在第 i 天,持有股票的最大利润是多少?
  • 在第 i 天,不持有股票的最大利润是多少?

通过解决这些子问题,我们可以逐步构建出全局最优解。

代码实现

以下是使用JavaScript实现动态规划解法的代码:

const maxProfit = (prices) => {
  if (prices.length === 0) return 0;

  const dp = new Array(prices.length).fill(0).map(() => new Array(2).fill(0));

  dp[0][0] = -prices[0];
  dp[0][1] = 0;

  for (let i = 1; i < prices.length; i++) {
    dp[i][0] = Math.max(dp[i - 1][0], -prices[i]);
    dp[i][1] = Math.max(dp[i - 1][1], dp[i - 1][0] + prices[i]);
  }

  return dp[prices.length - 1][1];
};

代码解释

  • 我们使用一个二位数组dp来存储子问题的解,其中dp[i][0]表示在第i天持有股票的最大利润,而dp[i][1]表示在第i天不持有股票的最大利润。
  • 我们从第 0 天开始,在第 0 天持有股票的最大利润显然是负股票价格,不持有股票的最大利润是 0。
  • 对于第i天,我们有两种选择:持有股票或不持有股票。如果我们持有股票,那么最大利润是前一天持有股票的最大利润减去今天的股票价格。如果我们不持有股票,那么最大利润是前一天不持有股票的最大利润或前一天持有股票的最大利润加上今天的股票价格,取较大值。
  • 通过这种方式,我们逐步构建出全局最优解,即在最后一天不持有股票的最大利润。

复杂度分析

  • 时间复杂度:O(n),其中 n 是股票价格数组的长度。
  • 空间复杂度:O(n),其中 n 是股票价格数组的长度。

总结

LeetCode《初级算法》中的动态规划问题“买卖股票的最佳时机”为程序员提供了练习动态规划技能的机会。通过使用JavaScript实现问题,我们展示了如何通过自顶向下地分解问题并解决子问题来解决复杂的问题。这种方法对于解决各种优化问题非常有用,在软件开发和其他领域都有着广泛的应用。