赞
踩
题目链接:
题目描述:
给你一个整数数组 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 。
示例 3:
输入:prices = [7,6,4,3,1]
输出:0
解释:在这种情况下, 交易无法获得正利润,所以不参与交易可以获得最大利润,最大利润为 0 。
提示:
1 <= prices.length <= 3 * 104
0 <= prices[i] <= 104
先说说贪心的解法吧:
贪心算法的思路是通过局部最优推得全局最优。这里把一买一卖看成一个交易,相邻2天就可以完成一个交易,只要交易有获利(局部获利)我们就进行,否则不进行。最终所有的局部获利之和就是所求全局最大获利,因为我们充分地利用了每次交易去获利了。具体代码如下:
- class Solution:
- def maxProfit(self, prices: List[int]) -> int:
- profit = 0#统计局部获利之和
- for i in range(1, len(prices)):
- if prices[i] > prices[i - 1]: profit += prices[i] - prices[i - 1]#如果后一天的股票价格比前一天高,那么我们就可以通过这次交易获利(前一天买进,后一天卖出)。累加局部获利
- return profit#局部获利累加结果即为全局最大获利
下面再说说动态规划的算法:
dp四部曲:
确定dp数组:dp[i][0]表示第i天不持有股票地最大利润,dp[i][1]表示第i天不持有股票地最大利润.
确定递推公式:dp[i][0]=max(dp[i-1][0], dp[i-1][1]+prices[i])表示第i天不持有股票地最大利润为max(前一天不持有股票地最大利润,前一天持有股票地最大利润+今天股票地价格即今天把股票卖了)。。。dp[i][1]=max(dp[i-1][1], dp[i-1][0]-prices[i])表示第i天持有股票地最大利润为max(前一天持有股票地最大利润,前一天没持有股票地最大利润-今天股票的价格即今天把股票买了)
初始化dp数组:dp[0][0]=0,dp[0][1]=-prices[0],其他都初始化为0
遍历顺序:顺序遍历,因为存在着前后依赖关系。因为dp[i]的情况只与dp[i-1]有关,所以考虑滚动数组,用dp00, dp01, dp10, dp11分别代替dp[i-1][0],dp[i-1][1],dp[i][0],dp[i][1]
代码如下:
- class Solution:
- def maxProfit(self, prices: List[int]) -> int:
- dp00, dp01, dp10, dp11 = 0, -prices[0], 0, 0#初始化dp值
- for i in range(1, len(prices)):
- dp10 = max(dp00, dp01 + prices[i])#第i天不持有股票的最大利润
- dp11 = max(dp01, dp00 - prices[i])#第i天持有股票的最大利润
- dp00 = dp10
- dp01 = dp11
- return dp10#返回最后一天不持有股票的最大利润,因为不持有股票的最大利润肯定是大于持有股票的最大利润的,把股票卖了钱肯定更多啊
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。