Skip to content

Commit dbfbb45

Browse files
Maximum Sum of 3 Non-Overlapping Subarrays : Accepted
1 parent 1269b67 commit dbfbb45

File tree

2 files changed

+125
-0
lines changed

2 files changed

+125
-0
lines changed

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,7 @@ My accepted leetcode solutions to some of the common interview problems.
109109
- [Maximum Subarray](problems/src/dynamic_programming/MaximumSubarray.java) (Easy)
110110
- [Dungeon Game](problems/src/dynamic_programming/DungeonGame.java) (Hard)
111111
- [2 Keys Keyboard](problems/src/dynamic_programming/TwoKeysKeyboard.java) (Medium)
112+
- [Maximum Sum of 3 Non-Overlapping Subarrays](problems/src/dynamic_programming/MaxSum3SubArray.java) (Hard)
112113

113114
#### [Greedy](problems/src/greedy)
114115

Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
package dynamic_programming;
2+
/**
3+
* Created by gouthamvidyapradhan on 22/11/2017.
4+
5+
In a given array nums of positive integers, find three non-overlapping subarrays with maximum sum.
6+
7+
Each subarray will be of size k, and we want to maximize the sum of all 3*k entries.
8+
9+
Return the result as a list of indices representing the starting position of each interval (0-indexed). If there are multiple answers, return the lexicographically smallest one.
10+
11+
Example:
12+
Input: [1,2,1,2,6,7,5,1], 2
13+
Output: [0, 3, 5]
14+
Explanation: Subarrays [1, 2], [2, 6], [7, 5] correspond to the starting indices [0, 3, 5].
15+
We could have also taken [2, 1], but an answer of [1, 3, 5] would be lexicographically larger.
16+
Note:
17+
nums.length will be between 1 and 20000.
18+
nums[i] will be between 1 and 65535.
19+
k will be between 1 and floor(nums.length / 3).
20+
21+
Solution:
22+
O(N) solution by prefix and reverse-prefix sum
23+
First calculate max index for array index k, then use this to calculate max index for two array indices j and k and
24+
again use this result to calculate the final max index for i, j and k for the 3 arrays.
25+
26+
*/
27+
public class MaxSum3SubArray {
28+
29+
class Max{
30+
int i, j, k, max;
31+
Max(int i, int max){
32+
this.i = i;
33+
this.max = max;
34+
}
35+
Max(int i, int j, int max){
36+
this.i = i;
37+
this.j = j;
38+
this.max = max;
39+
}
40+
}
41+
42+
/**
43+
* Main method
44+
* @param args
45+
* @throws Exception
46+
*/
47+
public static void main(String[] args) throws Exception{
48+
int[] A = {1,2,1,2,6};
49+
int[] result = new MaxSum3SubArray().maxSumOfThreeSubarrays(A, 1);
50+
for (int i = 0; i < result.length; i ++)
51+
System.out.print(result[i] + " ");
52+
}
53+
54+
public int[] maxSumOfThreeSubarrays(int[] nums, int k) {
55+
int[] fPrefix = new int[nums.length]; //forward prefix sum
56+
int[] rPrefix = new int[nums.length]; //reverse prefix sum
57+
58+
//calculate forward prefix sum
59+
for(int i = 0; i < k; i ++){
60+
fPrefix[0] += nums[i];
61+
}
62+
for(int i = 1; i < nums.length; i ++){
63+
if(i + k - 1 < nums.length){
64+
fPrefix[i] = fPrefix[i - 1] - nums[i - 1] + nums[i + k - 1];
65+
}
66+
}
67+
int sum = 0;
68+
for(int i = nums.length - 1; i >= nums.length - k; i --){
69+
sum += nums[i];
70+
}
71+
Max[] max1 = new Max[nums.length];
72+
max1[nums.length - k] = new Max(nums.length - k, sum);
73+
74+
//calculate reverse prefix sum
75+
rPrefix[nums.length - k] = sum;
76+
for(int i = nums.length - 1; i >= 0; i --){
77+
if(i + k >= nums.length) continue;
78+
rPrefix[i] = rPrefix[i + 1] - nums[i + k] + nums[i];
79+
}
80+
81+
//calculate max for k index
82+
for(int i = nums.length - 1; i >= 0; i --){
83+
if(i + k >= nums.length) continue;
84+
max1[i] = new Max(i, rPrefix[i]);
85+
if(max1[i + 1] != null){
86+
if(max1[i].max < max1[i + 1].max){
87+
max1[i] = new Max(max1[i + 1].i, max1[i + 1].max);
88+
}
89+
}
90+
}
91+
92+
//calculate max for j and k index
93+
Max[] max2 = new Max[nums.length];
94+
for(int i = nums.length - 1; i >= 0; i --){
95+
if(i + k < nums.length && max1[i + k] != null){
96+
max2[i] = new Max(i, max1[i + k].i, fPrefix[i] + max1[i + k].max);
97+
}
98+
}
99+
for(int i = nums.length - 1; i >= 0; i --){
100+
if(i + 1 > nums.length - 1 || max2[i + 1] == null) continue;
101+
if(max2[i].max < max2[i + 1].max){
102+
max2[i].max = max2[i + 1].max;
103+
max2[i].i = max2[i + 1].i;
104+
max2[i].j = max2[i + 1].j;
105+
}
106+
}
107+
108+
//calculate max for i, j and k index
109+
int[] result = new int[3];
110+
int max = 0;
111+
for(int i = 0; i < nums.length; i ++){
112+
if((i + k) < nums.length - 1 && max2[i + k] != null){
113+
int temp = fPrefix[i] + max2[i + k].max;
114+
if(temp > max){
115+
max = temp;
116+
result[0] = i;
117+
result[1] = max2[i + k].i;
118+
result[2] = max2[i + k].j;
119+
}
120+
}
121+
}
122+
return result;
123+
}
124+
}

0 commit comments

Comments
 (0)