leetcode122. 买卖股票的最佳时机||

本文介绍了如何使用动态规划和贪心算法解决寻找股票交易最大利润的问题。动态规划方法通过建立二维数组dp,分别表示不持有股票和持有股票时的最大利润,并通过迭代更新状态方程。贪心算法则通过寻找相邻两天买卖的正利润,累加得到总利润。两种方法在不同视角下解析了问题,提供了有效的解决方案。
摘要由CSDN通过智能技术生成

给你一个整数数组 prices ,其中 prices[i] 表示某支股票第 i 天的价格。

在每一天,你可以决定是否购买和/或出售股票。你在任何时候 最多 只能持有 一股 股票。你也可以先购买,然后在 同一天 出售。

返回 你能获得的 最大 利润 。

示例 1:

输入:prices = [7,1,5,3,6,4]
输出:7
解释:在第 2 天(股票价格 = 1)的时候买入,在第 3 天(股票价格 = 5)的时候卖出, 这笔交易所能获得利润 = 5 - 1 = 4 。
     随后,在第 4 天(股票价格 = 3)的时候买入,在第 5 天(股票价格 = 6)的时候卖出, 这笔交易所能获得利润 = 6 - 3 = 3 。
     总利润为 4 + 3 = 7 。
示例 2:

输入:prices = [1,2,3,4,5]
输出:4
解释:在第 1 天(股票价格 = 1)的时候买入,在第 5 天 (股票价格 = 5)的时候卖出, 这笔交易所能获得利润 = 5 - 1 = 4 。
     总利润为 4 。

题解

动态规划

对于每一天来说,有两种状态,持有股票和不持有股票,对于动态规划来说,我们要能够找到与上一个状态的关系,也就是找出状态方程,所以我们定义一个二维数组dp

  • dp[i][0]:表示第i天不持有股票所获得的最大利润
  • dp[i][1]:表示第i天持有股票所获得的最大利润

显然,我们要求的是最后一天不持有股票所获得的最大利润,那怎么推出动态方程呢?

对于前一天,也有这两种状态,那怎么由前一天推出这一天的状态呢,有两种情况

  • 对于今天不持有股票的,有可能是前一天就不持有股票,也有可能是前一天持有股票,在今天卖掉了,那我们求的是最大利润,所以要取两者中最大的
  • 同理也可以得出今天持有股票的情况
dp[i][0] = Math.max(dp[i - 1][1] + prices[i], dp[i - 1][0])
dp[i][1] = Math.max(dp[i - 1][1], dp[i - 1][0] - prices[i])

初始化

对于第一天来说,不持有股票利润就是0,持有股票利润是-prices[0]

具体代码

var maxProfit = function(prices) {
    // 动态规划解法
    const len = prices.length
    const dp = new Array(len).fill([]).map(v => new Array(2))
    dp[0][0] = 0, dp[0][1] = - prices[0]
    for(let i = 1; i < len; i++) {
        dp[i][0] = Math.max(dp[i - 1][1] + prices[i], dp[i - 1][0])
        dp[i][1] = Math.max(dp[i - 1][1], dp[i - 1][0] - prices[i])
    }

    return dp[len - 1][0]
};

贪心算法

这道题也可以使用贪心算法,但可能比较难想的出。。。

贪心算法要能够先找到子问题,那对于买卖股票来说,我们可以分成几个买卖的阶段,比如第1天买第2天卖出,第3天买第4天卖出,然后把每个阶段的利润合起来就是整个买卖过程的总利润了。这就变成通过这些子问题的最优解找到整个问题的最优解了

那对于买一个子问题也就是每一个买卖的过程,比如price[3] - price[1],第一天买入第3天卖出,那price[3] - price[1]也可以表示为(prices[3] - prices[2]) + (prices[2] - prices[1]) + (prices[1] - prices[0])

所以可以表示为相邻两天买卖的利润,但我们求的是最大利润,所以只选择利润值为正的就好

对于这里,为什么可以转化为这样,我的理解是:

  • 对于每一天,我都拿钱去买股票,然后第二天卖出去
  • 那如果卖出去亏了的话,那这一次就不买了
  • 那如果卖出去赚钱了,即卖出的前大于买入的钱,两种之差就是利润了

具体代码

var maxProfit = function(prices) {
    // 贪心解法
    let result = 0
    const len = prices.length
    for(let i = 1; i < len; i++) {
        if(prices[i] - prices[i - 1] > 0) {
            result += prices[i] - prices[i - 1]
        }
    }
    return result
};
根据引用\[1\]和引用\[2\]的内容,买卖股票最佳时机可以使用动态规划算法来解决。动态规划是一种通过将问题分解为子问题并利用子问题的解来求解原问题的方法。在这个问题中,我们可以定义一个状态数组dp,其中dp\[i\]表示第i天卖出股票所能获得的最大利润。然后,我们可以通过遍历价格数组prices,计算出每一天卖出股票所能获得的最大利润,并更新dp数组。最后,dp数组中的最后一个元素即为所求的最大利润。 根据引用\[3\]的内容,区间动态规划算法是解决买卖股票最佳时机问题的一种方法。在这个算法中,我们需要考虑每个可能的入和卖出的时间点,并计算出每个时间点的最大利润。然后,我们可以通过比较这些最大利润,找到最大的利润作为结果。 所以,买卖股票最佳时机可以使用区间动态规划算法来解决。 #### 引用[.reference_title] - *1* *3* [【算法-LeetCode】121. 买卖股票最佳时机动态规划;贪心)](https://blog.csdn.net/qq_44879358/article/details/120306943)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^control_2,239^v3^insert_chatgpt"}} ] [.reference_item] - *2* [【算法-LeetCode122. 买卖股票最佳时机 II(动态规划;贪心)](https://blog.csdn.net/qq_44879358/article/details/120783546)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^control_2,239^v3^insert_chatgpt"}} ] [.reference_item] [ .reference_list ]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值