Offer 驾到,掘友接招!我正在参与2022春招打卡活动,点击查看活动详情。
题目:给定一个价格数组,数组中元素代表每一天的股票价格,现要设计一个算法算出最大利润。在满足以下要求的前提下,可以完成即可能多的交易:
- 卖出股票后,第二天为冷冻期,该天不能买入股票。
- 不能同时持有多只股票,即再次购买前必须出售当前已有股票。
解题思路
之前做过一题买卖股票的最佳时机,对应LeetCode 121。那题的解决方法是动态规划,其中动态规划数组dp[i]
代表的是前i
天的最低价格,之后遍历每天的股票将该天价格减去之前最低价即可。
本题的思路也是动态规划,但多了一个冷冻期。那么所有可能的收益情况就变成:
- 当天持有股票的收益,我们假设以
dp[i][0]
来表示。 - 当天不持有股票且处于冷冻期的收益,我们假设以
dp[i][1]
来表示。 - 当前不持有股票且不处于冷冻期的收益,我们假设以
dp[i][2]
来表示。
那么上述情况就等价于:
dp[i][0]
当前天持有股票的收益 = max(前一天持有股票的收益,当前他买入股票的收益)dp[i][1]
当前天不持有股票且处于冷冻期的收益 = 当前天卖出了股票
dp[i][2]
当前天不持有股票且不处于冷冻期的收益 = max(前一天不持有股票且处于冷冻期, 前一天不持有股票且不处于冷冻期)
最后一天的情况就是当天不持有股票但无法确定是否处于冷冻期,有了以上分析,可得代码如下:
public int maxProfit(int[] prices) {
/**
* dp[i][0] 当前天持有股票的收益 = max(前一天持有股票的收益,当前他买入股票的收益)
* dp[i][0] = max(dp[i-1][0], dp[i-1][2]-prices[i])
* dp[i][1] 当前天不持有股票且处于冷冻期的收益 = 当前天卖出了股票
* dp[i][1] = dp[i-1][0] + prices[i]
* dp[i][2] 当前天不持有股票且不处于冷冻期的收益 = max(前一天不持有股票且处于冷冻期, 前一天不持有股票且不处于冷冻期)
* dp[i][2] = max(dp[i-1][1], dp[i-1][2])
*/
int len = prices.length;
int[][] dp = new int[len][3];
dp[0][0] = -prices[0];
dp[0][1] = 0;
dp[0][2] = 0;
for(int i=1;i<len;i++){
dp[i][0] = Math.max(dp[i-1][0], dp[i-1][2]-prices[i]);
dp[i][1] = dp[i-1][0] + prices[i];
dp[i][2] = Math.max(dp[i-1][1], dp[i-1][2]);
}
// 最终肯定是不持有股票是不知道是否处于冷冻期
return Math.max(dp[len-1][1], dp[len-1][2]);
}
复制代码
上述代码时间复杂度和空间复杂度都是。
© 版权声明
文章版权归作者所有,未经允许请勿转载。
THE END