题目描述
给定一个数组 prices ,它的第 i 个元素 prices[i] 表示一支给定股票第 i 天的价格。
你只能选择 某一天 买入这只股票,并选择在 未来的某一个不同的日子 卖出该股票。设计一个算法来计算你所能获取的最大利润。。
示例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。
思路及实现
My first method
截取
思路: 由于这两天在学习集合的知识,当看到这个题的时候,脑海中就涌现出用集合的嵌套来解决这个问题,定义一个Map集键用于存放利润,由于Map集合的键是不重复,无序,无索引的。所以这个方法只能展示一唯一的利润,重复的不会被存储,但也可以达到本题最大利润的要求,而对应的值则存放买入和卖出日期。
实现:
具体代码实现:
public class Demo1 {
public static void main(String[] args) {
int[] nums = {7,1,5,3,6,4};
int temp = 0;
Map<Integer, List<Integer>> day = new HashMap<>();
for (int i = 0; i < nums.length; i++) {
for (int j = i + 1; j < nums.length; j++) {
List<Integer> profit1 = new ArrayList<>();
int profit = nums[j] - nums[i];
if (profit > temp) {
Collections.addAll(profit1, i, j);
day.put(profit, profit1);
}
}
}
Set<Integer> keys = day.keySet();
int maxProfit = 0;
for (Integer key : keys) {
if(maxProfit < key){
maxProfit = key;
}
// List<Integer> value = day.get(key);
// System.out.println(key + "=>" + value);
}
System.out.println(maxProfit);
}
}
/*结果:5*/
My second method
两次遍历
思路: 定义一个变量记录最大值,通过两次遍历,得到最大值即可。但这种方法写的代码优雅程度往往太低,需要用到两个循环,但也是一种思路。
实现:
具体代码实现:
public class theBesTime1 {
public static void main(String[] args) {
int[] nums = {7,1,5,3,6,4};
int maxProfit = 0;
for (int i = 0; i < nums.length; i++) {
for (int j = i + 1; j < nums.length; j++) {
int profit = nums[j] - nums[i];
if(profit > maxProfit){
maxProfit = profit;
}
}
}
System.out.println(maxProfit);
}
}
/*结果:5*/
}
My third method
一次遍历
思路:
定义一个最小值在循环中,每判断一次,如果小于遍历到的数字小于最小值则把该值赋给最小值;如果不小于,则用该值与最小值作差,如果差大于最大值,则把该值赋给最大值,如果不大于,则代表前面已经存在的最大值仍是最大不需要赋值。
实现:
具体代码实现:
public class theBestTime2 {
public static void main(String[] args) {
int[] nums = {7,1,5,3,6,4};
int minPrice = nums[0];
int maxProfit = 0;
for (int i = 1; i < nums.length; i++) {
if(nums[i] < minPrice){
minPrice = nums[i];
} else if (maxProfit < (nums[i] - minPrice)) {
maxProfit = nums[i] - minPrice;
}
}
System.out.println(maxProfit);
}
}/*结果:5*/
收获
通过该算法的学习,我脑海中涌现的一个方法使用集合嵌套的思想,虽然可以实现,但却把问题复杂化。虽然复杂但也顺便复习一下Map集合的使用,即所谓熟能生巧。