力扣周末回顾2--122题 买卖股票的最好时机 II

这里是力扣回顾的第二题,与第一题相比,这道题有了一个算法思想,叫“贪心”。

如果真的有路过的同学,建议先做完第一题。

题目出处:点击此处

什么是贪心算法?
就是不从整体考虑,不断地追求局部问题的最优解,最后把所有局部问题汇总起来,就是总体最优解。

从我个人做题的遇到的困难出发,最容易陷入困惑的就是:
不断追求局部最优,最后的结果到底是不是整体最优?会不会有没考虑到的情况?

这个问题真的不能简单地下定论,有可能题目的考点不是“贪心”时,这个方法就会有问题,所以需要一些数学证明。

比如这道题,题目想要最大的利润,且可以无限次买卖。
根据第一题的解法,我们还是得画图
在这里插入图片描述
如果你没有做过第一题,其实很容易就想到了:
把所有上升段全部加起来,就是答案了啊。
恭喜你,做对了,而且这就是贪心追求的思路。

但是如果你做过第一题,就会有点瞻前顾后了,笔者就是这样的典例:
这个最低点会不会在跳跃几个最低点之后才会找到更好的利润啊?
答案是 不会!

为什么呢?
我们来看一下大神做出的数学解释,其实真的相当简单,我们要学会的就是这种思想。
在这里插入图片描述如图,
假如我在1点中买入,我觉得跳过3,在4卖出会更好啊,利益看起来好像更多,我们再看下面这幅图:
在这里插入图片描述我们把用x轴,y轴来理解:
4点的y轴-1点的y轴的差。
2点y轴-1点y轴的差 加上 4点的y轴- 3点的y轴的差

从图中我们明显看出,是后者比前者更大,这个推广出来,就回到我们一开始最简单的想法:
把所有上升段全部加起来,就是答案了啊。
问题到此就结束了,剩下的就是打代码的功夫。

个人感觉如果想不出其他办法,又不想用暴力的时候,可以先撸一串“贪心”

以下是代码:

class Solution {
    public int maxProfit(int[] prices) {
        if( prices.length == 0){
            return 0;
        }
        int max = 0;
        int lowp = prices[0];
        int height = 0;
        for(int i = 0; i < prices.length - 1 ; i++){
            while( i <prices.length -1 && prices[i] > prices[i+1]){
                i++;
            }
            lowp = prices[i];
            while( i< prices.length -1 && prices[i] < prices[i+1]){
                i++;
            }
            height = prices[i];
            max += (height-lowp);
        }
        return max;
    }
}

以下是敲过一边代码之后才会发现的坑:

1.开始的lowp点依然要设置为prises[0];

2.依然要考虑prises数组为空的情况;

  1. 仔细考虑最后一个点的情况,想想三个while为什么可以把最后一个点纳入考虑;

4.有更好的解法,比如:只要当前值比之前上升,就加上去,空间复杂度更小。

下面是第一次见到这题打的代码,因为很菜,只留做记录,大家不要学习。

class Solution {
    public int maxProfit(int[] prices) {
        int L = prices.length;
        boolean flag = true;
        int maxPf = 0;
        int temp = 0;
        for(int i = 0; i<L;i++)
        {
        	//如果是买
        	if(flag) {
        		if( (i != L-1) && (prices[i+1] <= prices[i])) {continue;}
        		if( i == L-1) {break;}
        		temp  = prices[i];
        		flag = false;
        		continue;
        	}
        	//如果是卖
        	if(!flag) {
        		if( ( i != L-1) && (prices[i+1] >= prices[i]) ) {continue;}
        		if( i == L-1)
        		{
            		maxPf = maxPf + prices[i] - temp;
            		break;
        		}
        		maxPf = maxPf + prices[i] - temp;
        		flag = true;
        		continue;
        	}
        }
        return maxPf;
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值