Question
Say you have an array for which the ith element is the price of a given stock on day i.
Design an algorithm to find the maximum profit. You may complete at most two transactions.
Note:
You may not engage in multiple transactions at the same time (ie, you must sell the stock before you buy again).
Stats
Frequency | 1 |
Difficulty | 4 |
Adjusted Difficulty | 4 |
Time to use | -------- |
Ratings/Color = 1(white) 2(lime) 3(yellow) 4/5(red)
Analysis
This is much harder to solve then previous 2 question combined.
Solution
The best solution is explained in this blog.
we can just dived the whole prices array at every point, try to calculate max profit from left and from right respectively…
However, there are many repeat calculations. So we can apply DP to record max profits for each left side and right side. then add them together at each point.
A detailed illustration with examples can be found here.
However, the coding part is slightly difficult at least for me. I made a terrible mistake with the variable ‘leftMin’ and ‘rightMax’. I declared it as ‘rightMin’ instead, and then the program logic is wrong. We should avoid this kind of mistakes.
Code
public int maxProfit(int[] prices) {
int len = prices.length;
if (len == 0) return 0;
int leftMin = Integer.MAX_VALUE, rightMax = Integer.MIN_VALUE;
int leftPro[] = new int[len], rightPro[] = new int[len];
for (int j = 0; j <= len - 1; j ++) {
leftMin = Math.min(leftMin, prices[j]);
if (j == 0) leftPro[0] = 0;
else leftPro[j] = Math.max(leftPro[j-1], prices[j] - leftMin);
}
for (int k = len - 1; k >= 0; k --) {
rightMax = Math.max(rightMax, prices[k]);
if (k == len - 1) rightPro[len-1] = 0;
else rightPro[k] = Math.max(rightPro[k+1], rightMax - prices[k]);
}
int totalPro = 0;
for (int i = 0; i < len; i ++) {
totalPro = Math.max(totalPro, leftPro[i] + rightPro[i]);
}
return totalPro;
}