您的位置:首页 > 其它

best-time-to-buy-and-sell-stock(购买并抛售股票的最佳时机)

2018-03-23 23:01 399 查看

题目1

(1)题目:假设你有一个数组,其中第i个元素是第i天给定股票的价格。
如果您只允许完成至多一笔交易(即买入一只股票并出售一只股票),则设计一种算法以找到最大利润。
(2)分析:分别计算第1天,第2天,...,第n-1天出售股票时的最大利润,再得出总的最大利润。
(3)代码:


代码1:

public class Solution {
public int maxProfit(int[] prices) {
if(prices==null || prices.length<=1) return 0;
int n=prices.length;
int max=0;
for(int i=1;i<n;i++){
for(int j=0;j<i;j++){//第i+1天出售股票
max=Math.max(max,prices[i]-prices[j]);
}
}
return max;
}
}


代码2:保存每个最小值点,更新维护该值后面较大值和最小值的差

来自牛客网

public class Solution {
public int maxProfit(int[] prices) {
if(prices==null||prices.length==0){
return 0;
}
int max=0;
int min=prices[0];
for(int i=0;i<prices.length;i++){
min = Math.min(min,prices[i]);
max=Math.max(max,prices[i]-min);
}
return max;
}
}


题目2

(1)题目:假设你有一个数组,其中第i个元素是第i天给定股票的价格。设计一个算法来找到最大的利润。 您最多可以完成两笔交易。
注意:您不可以同时进行多笔交易(即您必须在再次购买之前出售股票)。
(2)分析:假设第i天为第一次出售股票的时间,计算第0天到第i天的最大利润;再分析第i+1天到第n-1天购买和出售股票的最大利润(当然这段时间内也可以没有交易)。最大利润为两者之和。
(3)代码:


代码1:

public class Solution {

public int maxProfit(int[] prices) {
if(prices==null || prices.length==0) return 0;
return maxProfit(prices,0,prices.length-1);
}

public int maxProfit(int [] array,int start,int end){
if(start>=end) return 0;
int max=0;
for(int i=start+1;i<=end;i++){
max=Math.max(max,maxProfit1(array,start,i)+maxProfit2(array,i+1,end));
}
return max;
}

public int maxProfit1(int [] array,int start,int end){//计算第i天出售股票时的最大利润
if(start>=end) return 0;
int max=0;
for(int i=start;i<end;i++){
max=Math.max(max,array[end]-array[i]);
}
return max;
}

public int maxProfit2(int [] array,int start,int end){//计算第i+1到第n天购买和出售股票的最大利润
if(start>=end) return 0;
int max=0;
for(int i=start;i<end;i++){
for(int j=i+1;j<=end;j++){
max=Math.max(max,array[j]-array[i]);
}
}
return max;
}
}


代码2:来自牛客网

/**
* 分别计算出i之前和之后的最大利润pre[i],post[i]
* 再以i为分割求出两次交易的最大利润(在i处可能卖出再买入,相当于就一次交易)
* 空间换时间,时间复杂度O(n),空间复杂度O(n)
* @param prices
* @return
*/
public int maxProfit(int[] prices) {
if(prices==null||prices.length<2) return 0;
int[]pre=new int[prices.length];
int []post=new int[prices.length];
int min=prices[0];
for(int i=1;i<prices.length;i++){
min=Math.min(min,prices[i]);
pre[i]=Math.max(pre[i-1],prices[i]-min);
}
int max=prices[prices.length-1];
for(int i=prices.length-2;i>=0;i--){
max=Math.max(max,prices[i]);
post[i]=Math.max(post[i+1],max-prices[i]);
}
int maxProfit=0;
for(int i=0;i<prices.length;i++){
maxProfit=Math.max(maxProfit,pre[i]+post[i]);
}
return  maxProfit;
}


题目3

(1)题目:假设你有一个数组,其中第i个元素是第i天给定股票的价格。设计一个算法来找到最大的利润。 您可以根据需要完成尽可能多的交易(即多次买入和卖出一次股票)。 但是,您不得同时进行多笔交易(即您必须在再次购买之前出售股票)。
(2)分析:假设第i天为第一次出售股票的时间,计算出第0天到第i天这段时间的最大利润。然后再计算第i+1天到第n天这段时间的最大利润,这是一个递归求解的过程。
(3)代码:


代码1:该算法因为用到了递归,导致时间复杂度太大。

public class Solution {

public int maxProfit(int[] prices) {
if(prices==null || prices.length<=1) return 0;
return maxProfit(prices,0,prices.length-1);
}

public int maxProfit(int [] array,int start,int end){
if(start>=end) return 0;
int max=0;
for(int i=start+1;i<=end;i++){
max=Math.max(max,maxProfit1(array,start,i)+maxProfit(array,i+1,end));
}
return max;
}

public int maxProfit1(int [] array,int start,int end){
if(start>=end) return 0;
int max=0;
for(int i=start;i<end;i++){
max=Math.max(max,array[end]-array[i]);
}
return max;
}

}


代码2:来自牛客网

class Solution {
public:
int maxProfit(vector<int> &prices) {
//本题由于允许多次交易(每次必须先卖出再买进),所以不好用爆搜
//分析可知,要想利益最大化,就应该每次在波谷买进,波峰卖出,这样利益最大,操作次数最少。
//波峰减波谷等于波峰到波谷的元素依次相减的和
//应该是使用动态规划来做可能比较简洁,个人觉得。

int len = prices.size();
vector<int> change(len,0);
int maxPro=0;
for(int i=1;i<len;i++){
change[i]=prices[i]-prices[i-1];  //记录所有长和跌的情况
if(change[i]>0)maxPro += change[i];  //累加所有长幅,即为最大收益
}
return maxPro;
}
};


题目1来自牛客网leetcode

题目2来自牛客网leetcode

题目3来自牛客网leetcode
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐