[LeetCode] DP之 Best time to buy and sell stock with transaction fee

来源:互联网 发布:matlab利用空矩阵赋值 编辑:程序博客网 时间:2024/06/07 11:59

题目

题目描述

分析

这题是我很少做过的dp,和之前那个树的最小和问题有点像,因为它是有多个状态交错依赖的。这题中有四个行为:

  • 没有股票的情况下:买股票
  • 没有股票的情况下:什么也不做
  • 有股票的情况下:卖股票
  • 有股票的情况下:什么也不做

它特殊的地方就在于不止有买卖这两种操作,还有有没有股票的持有与否。所以比较明确的思路就需要四个数组。当然,这在之后可以进行优化。然后的思路就很简单了
你要买,就必须之前没有股票
要卖,必须之前有股票
这都是非常显然的。在代码中有详细注释

时间复杂度分析

时间复杂度是遍历一次的复杂度,为O(n),这可已经是最小的了,但是可以控制数组的个数。

代码

首先放出一个非常好理解的版本

class Solution{  public:    int maxProfit(vector<int> &prices, int fee) {        // buy a stock on day i        vector<int> buy(prices.size(), 0);        // sell a stock on day i        vector<int> sell(prices.size(), 0);        // we don't have a stock and do nothing on day i        vector<int> notHold(prices.size(), 0);        // we have a stock and do nothing on day i        vector<int> hold(prices.size(), 0);        buy[0] = hold[0] = 0- prices[0];        for (int i = 1; i < prices.size(); i++) {            // we can buy a stock only if we don't have a stock on day i-1            buy[i] = max(sell[i-1], notHold[i-1]) - prices[i];            // we can sell a stock only if we have a stock on day i-1            sell[i] = max(hold[i-1], buy[i-1]) + prices[i] - fee;            // we can hold a stock only if we have a stock on day i-1            hold[i] = max(hold[i-1], buy[i-1]);            // we can notHold a stock only if we don't have a stock on day i            notHold[i] = max(notHold[i-1], sell[i-1]);        }        int ans = max(buy[prices.size() - 1], sell[prices.size() - 1]);        int ans2 = max(notHold[prices.size() - 1], hold[prices.size() - 1]);        return max(ans, ans2);    }};

简单的观察后,就可以进行优化

class Solution{  public:    int maxProfit(vector<int> &prices, int fee) {        // buy a stock on day i        int buy = 0 - prices[0];        // sell a stock on day i        int sell = 0;        // we don't have a stock and do nothing on day i        int notHold = 0;        // we have a stock and do nothing on day i        int hold = 0 - prices[0];        for (int i = 1; i < prices.size(); i++) {            // we can notHold a stock only if we don't have a stock on day i            notHold = max(notHold, sell);            // we can hold a stock only if we have a stock on day i-1            hold = max(hold, buy);            // we can buy a stock only if we don't have a stock on day i-1            buy = notHold - prices[i];            // we can sell a stock only if we have a stock on day i-1            sell = hold + prices[i] - fee;        }        int ans = max(buy, sell);        int ans2 = max(notHold, hold);        return max(ans, ans2);    }};

当然,可以有更多优化,但是这种思路比较清楚,因此就只放出这两个。

阅读全文
0 0
原创粉丝点击