121.
给定一个数组 prices
,它的第 i
个元素 prices[i]
表示一支给定股票第 i
天的价格。你只能选择 某一天 买入这只股票,并选择在 未来的某一个不同的日子 卖出该股票。设计一个算法来计算你所能获取的最大利润。返回你可以从这笔交易中获取的最大利润。如果你不能获取任何利润,返回 0
。
示例 1:
输入:[7,1,5,3,6,4] 输出:5 解释:在第 2 天(股票价格 = 1)的时候买入,在第 5 天(股票价格 = 6)的时候卖出,最大利润 = 6-1 = 5 。 注意利润不能是 7-1 = 6, 因为卖出价格需要大于买入价格;同时,你不能在买入前卖出股票。
示例 2:
输入:prices = [7,6,4,3,1] 输出:0 解释:在这种情况下, 没有交易完成, 所以最大利润为 0。
提示:
1 <= prices.length <= 105
0 <= prices[i] <= 104
122.
给你一个整数数组 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
121题的思路:注意,整个周期内,股价最高点可能在股价最低点的左边,这个差价是无法获得的,我们只能想办法找到某个最大的上涨周期,这个周期也可能不是一直涨,而是有涨有跌,总体向上。
如上图所示,很明显可以看出,应该在两个蓝色横线处买卖。整个周期内最低点是绿色划线处,但无法操作获取最大值,黄色划线处虽然是从低点上涨的小周期最大点,但不是整个周期最大点。
所以,我们的算法就是从prices[0]开始遍历,找到这段时期股票的最小值的日期i,设置股票最小值
minprice = prices[i]; 就是上图左边蓝色划线处的点。
那么怎么样才能收益最大呢?那就是往后遍历到某个日期i,这个日期i的股票值是从上一步最低价到现在这个周期里最高的价格的点,这段时间,股票都是上涨的,prices[i] - minprice就是当前这个上涨时间段里面的最大利润,设置为maxprofit。
继续遍历,上一步之后股价下跌或横盘了,就开始找新的最低价和最高价,如果有股价更低的点时,更新minprice,比如说上图绿色的点的值。
当后续还有上涨的情况时,找到新的最高价的点i,求出这个时间段的最大利润prices[i] - minprice,比较这个利润与之前所有上涨期内的记录下的最大的那个利润值maxprofit,让maxprofit等于这两个值中的最大那个值。
重复上面步骤直到遍历完成。
注意,因为在for循环中找最低点和最高点时,用的都是变量i,是先找到最低值,再找最高值,不会出现先卖后买的情况。
public class Solution {
public int maxProfit(int prices[]) {
int minprice = Integer.MAX_VALUE;
int maxprofit = 0;
for (int i = 0; i < prices.length; i++) {
if (prices[i] < minprice) {
minprice = prices[i];
} else if (prices[i] - minprice > maxprofit) {
maxprofit = prices[i] - minprice;
}
}
return maxprofit;
}
}
122题的思路
只要第二天上涨那就今天买,明天卖,在所有上涨的周期内都进行买卖操作,在下跌和横盘的时候不操作即可。
和上一题都注意股票没有开盘或者只有一天有值的情况,直接就返回0。
其实这里有个问题,现实中是无法预测第二天涨跌的,所以不存在每次最低点买,最高点卖。但是题目给的示例结果显示的是知道所有的涨跌了,那就这样计算。
class Solution {
public int maxProfit(int[] prices) {
int n = prices.length;
int buyTime = 0;
int sellTime = 1;
int [] profit = {0};
if (n <= 1){
return 0;
}
for (int i = 0; i < n - 1; i++){
if (prices[i] <= prices[i + 1]) {
profit[0] += prices[i + 1] - prices[i];
}
}
return profit[0];
}
}