123.Best Time to Buy and Sell Stock III---dp

题目连接:https://leetcode.com/problems/best-time-to-buy-and-sell-stock-iii/description/数组

题目大意:与122题相似,只是这里要求买卖次数只能有两次,计算两次总共的最大利润值。ide

法一(超时):计算某一天以前的最大利润值与某一天以后的最大利润值,而后用for循环遍历获得最大值,时间复杂度是o(n^2),代码以下:post

 1 int res = 0;
 2         for(int i = 0; i < prices.length; i++) {
 3             int maxPre = 0;
 4             int min = Integer.MAX_VALUE;
 5             //0 to i-1
 6             for(int j = 0; j < i; j++) {
 7                 if(prices[j] < min) {
 8                     min = prices[j];
 9                 }
10                 else if(prices[j] - min > maxPre){
11                     maxPre = prices[j] - min;
12                 }
13             }
14             //i to n-1
15             int maxPost = 0;
16             min = Integer.MAX_VALUE;
17             for(int j = i; j < prices.length; j++) {
18                 if(prices[j] < min) {
19                     min = prices[j];
20                 }
21                 else if(prices[j] - min > maxPost){
22                     maxPost = prices[j] - min;
23                 }
24             }
25             
26             if(maxPre + maxPost > res) {
27                 res = maxPre + maxPost;
28             }
29         }
30         return res;
View Code

法二(借鉴):动态规划,利用法一的思路,只是这里不用for循环嵌套遍历获得最大值,而是用两个数组分别记录某一天以前的最大利润值和某一天以后的最大利润值,而后再另开一个for循环,计算比较获得最大值。这里有两个动规公式:spa

1.数组记录最大利润:.net

  1)某一天以前:preProfit[i] = max(preProfit[i - 1], prices[i] - min);code

  2)某一天以后:postProfit[i] = max(postProfit[i + 1], max - prices[i]);blog

2.for循环计算获得最大值:res = max(res, preProfit[i] + postProfit[i]);ip

代码以下(耗时1ms):leetcode

 1         int length = prices.length;
 2         int[] preProfit = new int[length];
 3         int[] postProfit = new int[length];
 4         //从前日后找,0 to i,用数组记录每一天i以前所能得到的最大利润,计算过程与121题相似
 5         int minPrice = Integer.MAX_VALUE;
 6         int max = 0;
 7         for(int i = 0; i < length; i++) {
 8             if(prices[i] < minPrice) {
 9                 minPrice = prices[i];
10             }
11             else if(prices[i] - minPrice > max) {
12                 max = prices[i] - minPrice;
13             }
14             preProfit[i] = max;
15         }
16         //从后往前,i to n-1,用数组记录每一天i以后所能得到的最大利润
17         //注意:从后往前找的时候,应该记录当前位置以后的最大价值,而后将当前位置的价值与最大价值进行比较
18         int maxPrice = Integer.MIN_VALUE;
19         max = 0;
20         for(int i = length - 1; i >= 0; i--) {
21             if(prices[i] > maxPrice) {
22                 maxPrice = prices[i];
23             }
24             else if(maxPrice - prices[i] > max) {
25                 max = maxPrice - prices[i];
26             }
27             postProfit[i] = max;
28         }
29         
30         int res = 0;
31         for(int i = 0; i < length; i++) {
32             if(preProfit[i] + postProfit[i] > res) {
33                 res = preProfit[i] + postProfit[i];
34             }
35         }
36         return res;
View Code

 法三(借鉴):参考:http://blog.csdn.net/u012501459/article/details/46514309解法二。get

相关文章
相关标签/搜索