# Maximum Subarray Sum using Divide and Conquer algorithm

You are given a one dimensional array that may contain both positive and negative integers, find the sum of contiguous subarray of numbers which has the largest sum.

For example, if the given array is {-2, -5, 6, -2, -3, 1, 5, -6}, then the maximum subarray sum is 7 (see highlighted elements).

## Recommended: Please solve it on “PRACTICE ” first, before moving on to the solution.

The naive method is to run two loops. The outer loop picks the beginning element, the inner loop finds the maximum possible sum with first element picked by outer loop and compares this maximum with the overall maximum. Finally return the overall maximum. The time complexity of the Naive method is O(n^2).

Using Divide and Conquer approach, we can find the maximum subarray sum in O(nLogn) time. Following is the Divide and Conquer algorithm.

1) Divide the given array in two halves
2) Return the maximum of following three
….a) Maximum subarray sum in left half (Make a recursive call)
….b) Maximum subarray sum in right half (Make a recursive call)
….c) Maximum subarray sum such that the subarray crosses the midpoint

The lines 2.a and 2.b are simple recursive calls. How to find maximum subarray sum such that the subarray crosses the midpoint? We can easily find the crossing sum in linear time. The idea is simple, find the maximum sum starting from mid point and ending at some point on left of mid, then find the maximum sum starting from mid + 1 and ending with sum point on right of mid + 1. Finally, combine the two and return.

## C++

 `// A Divide and Conquer based program for maximum subarray sum problem ` `#include ` `#include ` ` `  `// A utility funtion to find maximum of two integers ` `int` `max(``int` `a, ``int` `b) { ``return` `(a > b)? a : b; } ` ` `  `// A utility funtion to find maximum of three integers ` `int` `max(``int` `a, ``int` `b, ``int` `c) { ``return` `max(max(a, b), c); } ` ` `  `// Find the maximum possible sum in arr[] auch that arr[m] is part of it ` `int` `maxCrossingSum(``int` `arr[], ``int` `l, ``int` `m, ``int` `h) ` `{ ` `    ``// Include elements on left of mid. ` `    ``int` `sum = 0; ` `    ``int` `left_sum = INT_MIN; ` `    ``for` `(``int` `i = m; i >= l; i--) ` `    ``{ ` `        ``sum = sum + arr[i]; ` `        ``if` `(sum > left_sum) ` `          ``left_sum = sum; ` `    ``} ` ` `  `    ``// Include elements on right of mid ` `    ``sum = 0; ` `    ``int` `right_sum = INT_MIN; ` `    ``for` `(``int` `i = m+1; i <= h; i++) ` `    ``{ ` `        ``sum = sum + arr[i]; ` `        ``if` `(sum > right_sum) ` `          ``right_sum = sum; ` `    ``} ` ` `  `    ``// Return sum of elements on left and right of mid ` `    ``// returning only left_sum + right_sum will fail for [-2, 1] ` `    ``return` `max(left_sum + right_sum, left_sum, right_sum); ` `} ` ` `  `// Returns sum of maxium sum subarray in aa[l..h] ` `int` `maxSubArraySum(``int` `arr[], ``int` `l, ``int` `h) ` `{ ` `   ``// Base Case: Only one element ` `   ``if` `(l == h) ` `     ``return` `arr[l]; ` ` `  `   ``// Find middle point ` `   ``int` `m = (l + h)/2; ` ` `  `   ``/* Return maximum of following three possible cases ` `      ``a) Maximum subarray sum in left half ` `      ``b) Maximum subarray sum in right half ` `      ``c) Maximum subarray sum such that the subarray crosses the midpoint */` `   ``return` `max(maxSubArraySum(arr, l, m), ` `              ``maxSubArraySum(arr, m+1, h), ` `              ``maxCrossingSum(arr, l, m, h)); ` `} ` ` `  `/*Driver program to test maxSubArraySum*/` `int` `main() ` `{ ` `   ``int` `arr[] = {2, 3, 4, 5, 7}; ` `   ``int` `n = ``sizeof``(arr)/``sizeof``(arr); ` `   ``int` `max_sum = maxSubArraySum(arr, 0, n-1); ` `   ``printf``(``"Maximum contiguous sum is %dn"``, max_sum); ` `   ``getchar``(); ` `   ``return` `0; ` `} `

## Java

 `// A Divide and Conquer based Java  ` `// program for maximum subarray sum ` `// problem ` `import` `java.util.*; ` ` `  `class` `GFG { ` ` `  `    ``// Find the maximum possible sum in arr[]  ` `    ``// such that arr[m] is part of it ` `    ``static` `int` `maxCrossingSum(``int` `arr[], ``int` `l, ` `                                ``int` `m, ``int` `h) ` `    ``{ ` `        ``// Include elements on left of mid. ` `        ``int` `sum = ``0``; ` `        ``int` `left_sum = Integer.MIN_VALUE; ` `        ``for` `(``int` `i = m; i >= l; i--) ` `        ``{ ` `            ``sum = sum + arr[i]; ` `            ``if` `(sum > left_sum) ` `            ``left_sum = sum; ` `        ``} ` ` `  `        ``// Include elements on right of mid ` `        ``sum = ``0``; ` `        ``int` `right_sum = Integer.MIN_VALUE; ` `        ``for` `(``int` `i = m + ``1``; i <= h; i++) ` `        ``{ ` `            ``sum = sum + arr[i]; ` `            ``if` `(sum > right_sum) ` `            ``right_sum = sum; ` `        ``} ` ` `  `        ``// Return sum of elements on left ` `        ``// and right of mid ` `       ``// returning only left_sum + right_sum will fail for [-2, 1] ` `        ``return` `Math.max(left_sum + right_sum, Math.max(left_sum, right_sum)); ` `    ``} ` ` `  `    ``// Returns sum of maxium sum subarray  ` `    ``// in aa[l..h] ` `    ``static` `int` `maxSubArraySum(``int` `arr[], ``int` `l,  ` `                                      ``int` `h) ` `    ``{ ` `    ``// Base Case: Only one element ` `    ``if` `(l == h) ` `        ``return` `arr[l]; ` ` `  `    ``// Find middle point ` `    ``int` `m = (l + h)/``2``; ` ` `  `    ``/* Return maximum of following three  ` `    ``possible cases: ` `    ``a) Maximum subarray sum in left half ` `    ``b) Maximum subarray sum in right half ` `    ``c) Maximum subarray sum such that the  ` `    ``subarray crosses the midpoint */` `    ``return` `Math.max(Math.max(maxSubArraySum(arr, l, m), ` `                    ``maxSubArraySum(arr, m+``1``, h)), ` `                    ``maxCrossingSum(arr, l, m, h)); ` `    ``} ` ` `  `    ``/* Driver program to test maxSubArraySum */` `    ``public` `static` `void` `main(String[] args) ` `    ``{ ` `    ``int` `arr[] = {``2``, ``3``, ``4``, ``5``, ``7``}; ` `    ``int` `n = arr.length; ` `    ``int` `max_sum = maxSubArraySum(arr, ``0``, n-``1``); ` `     `  `    ``System.out.println(``"Maximum contiguous sum is "``+ ` `                                         ``max_sum); ` `    ``} ` `} ` `// This code is contributed by Prerna Saini `

## Python3

 `# A Divide and Conquer based program ` `# for maximum subarray sum problem ` ` `  `# Find the maximum possible sum in ` `# arr[] auch that arr[m] is part of it ` `def` `maxCrossingSum(arr, l, m, h) : ` `     `  `    ``# Include elements on left of mid. ` `    ``sm ``=` `0``; left_sum ``=` `-``10000` `     `  `    ``for` `i ``in` `range``(m, l``-``1``, ``-``1``) : ` `        ``sm ``=` `sm ``+` `arr[i] ` `         `  `        ``if` `(sm > left_sum) : ` `            ``left_sum ``=` `sm ` `     `  `     `  `    ``# Include elements on right of mid ` `    ``sm ``=` `0``; right_sum ``=` `-``1000` `    ``for` `i ``in` `range``(m ``+` `1``, h ``+` `1``) : ` `        ``sm ``=` `sm ``+` `arr[i] ` `         `  `        ``if` `(sm > right_sum) : ` `            ``right_sum ``=` `sm ` `     `  ` `  `    ``# Return sum of elements on left and right of mid ` `    ``# returning only left_sum + right_sum will fail for [-2, 1] ` `    ``return` `max``(left_sum ``+` `right_sum, left_sum, right_sum) ` ` `  ` `  `# Returns sum of maxium sum subarray in aa[l..h] ` `def` `maxSubArraySum(arr, l, h) : ` `     `  `    ``# Base Case: Only one element ` `    ``if` `(l ``=``=` `h) : ` `        ``return` `arr[l] ` ` `  `    ``# Find middle point ` `    ``m ``=` `(l ``+` `h) ``/``/` `2` ` `  `    ``# Return maximum of following three possible cases ` `    ``# a) Maximum subarray sum in left half ` `    ``# b) Maximum subarray sum in right half ` `    ``# c) Maximum subarray sum such that the  ` `    ``#     subarray crosses the midpoint  ` `    ``return` `max``(maxSubArraySum(arr, l, m), ` `               ``maxSubArraySum(arr, m``+``1``, h), ` `               ``maxCrossingSum(arr, l, m, h)) ` `             `  ` `  `# Driver Code ` `arr ``=` `[``2``, ``3``, ``4``, ``5``, ``7``] ` `n ``=` `len``(arr) ` ` `  `max_sum ``=` `maxSubArraySum(arr, ``0``, n``-``1``) ` `print``(``"Maximum contiguous sum is "``, max_sum) ` ` `  `# This code is contributed by Nikita Tiwari. `

## C#

 `// A Divide and Conquer based C#  ` `// program for maximum subarray sum ` `// problem ` `using` `System; ` ` `  `class` `GFG { ` ` `  `    ``// Find the maximum possible sum in arr[]  ` `    ``// such that arr[m] is part of it ` `    ``static` `int` `maxCrossingSum(``int` `[]arr, ``int` `l, ` `                                ``int` `m, ``int` `h) ` `    ``{ ` `        ``// Include elements on left of mid. ` `        ``int` `sum = 0; ` `        ``int` `left_sum = ``int``.MinValue; ` `        ``for` `(``int` `i = m; i >= l; i--) ` `        ``{ ` `            ``sum = sum + arr[i]; ` `            ``if` `(sum > left_sum) ` `                ``left_sum = sum; ` `        ``} ` ` `  `        ``// Include elements on right of mid ` `        ``sum = 0; ` `        ``int` `right_sum = ``int``.MinValue;; ` `        ``for` `(``int` `i = m + 1; i <= h; i++) ` `        ``{ ` `            ``sum = sum + arr[i]; ` `            ``if` `(sum > right_sum) ` `                ``right_sum = sum; ` `        ``} ` ` `  `        ``// Return sum of elements on left ` `        ``// and right of mid ` `        ``// returning only left_sum + right_sum will fail for [-2, 1] ` `        ``return` `Math.Max(left_sum + right_sum, Math.Max(left_sum, right_sum)); ` `    ``} ` ` `  `    ``// Returns sum of maxium sum subarray  ` `    ``// in aa[l..h] ` `    ``static` `int` `maxSubArraySum(``int` `[]arr, ``int` `l,  ` `                                        ``int` `h) ` `    ``{ ` `         `  `    ``// Base Case: Only one element ` `    ``if` `(l == h) ` `        ``return` `arr[l]; ` ` `  `    ``// Find middle point ` `    ``int` `m = (l + h)/2; ` ` `  `    ``/* Return maximum of following three  ` `    ``possible cases: ` `    ``a) Maximum subarray sum in left half ` `    ``b) Maximum subarray sum in right half ` `    ``c) Maximum subarray sum such that the  ` `    ``subarray crosses the midpoint */` `    ``return` `Math.Max(Math.Max(maxSubArraySum(arr, l, m), ` `                          ``maxSubArraySum(arr, m+1, h)), ` `                         ``maxCrossingSum(arr, l, m, h)); ` `    ``} ` ` `  `    ``/* Driver program to test maxSubArraySum */` `    ``public` `static` `void` `Main() ` `    ``{ ` `        ``int` `[]arr = {2, 3, 4, 5, 7}; ` `        ``int` `n = arr.Length; ` `        ``int` `max_sum = maxSubArraySum(arr, 0, n-1); ` `         `  `        ``Console.Write(``"Maximum contiguous sum is "``+ ` `                                            ``max_sum); ` `    ``} ` `} ` ` `  `// This code is contributed by vt_m. `

## PHP

 `= ``\$l``; ``\$i``--)  ` `    ``{  ` `        ``\$sum` `= ``\$sum` `+ ``\$arr``[``\$i``];  ` `        ``if` `(``\$sum` `> ``\$left_sum``)  ` `        ``\$left_sum` `= ``\$sum``;  ` `    ``}  ` ` `  `    ``// Include elements on right of mid  ` `    ``\$sum` `= 0;  ` `    ``\$right_sum` `= PHP_INT_MIN;  ` `    ``for` `(``\$i` `= ``\$m` `+ 1; ``\$i` `<= ``\$h``; ``\$i``++)  ` `    ``{  ` `        ``\$sum` `= ``\$sum` `+ ``\$arr``[``\$i``];  ` `        ``if` `(``\$sum` `> ``\$right_sum``)  ` `        ``\$right_sum` `= ``\$sum``;  ` `    ``}  ` ` `  `    ``// Return sum of elements on left ` `    ``// and right of mid  ` `    ``// returning only left_sum + right_sum will fail for [-2, 1] ` `    ``return` `max(``\$left_sum` `+ ``\$right_sum``, ``\$left_sum``, ``\$right_sum``);  ` `}  ` ` `  `// Returns sum of maxium sum  ` `// subarray in aa[l..h]  ` `function` `maxSubArraySum(&``\$arr``, ``\$l``, ``\$h``)  ` `{  ` `    ``// Base Case: Only one element  ` `    ``if` `(``\$l` `== ``\$h``)  ` `        ``return` `\$arr``[``\$l``];  ` `     `  `    ``// Find middle point  ` `    ``\$m` `= ``intval``((``\$l` `+ ``\$h``) / 2);  ` `     `  `    ``/* Return maximum of following three possible cases  ` `        ``a) Maximum subarray sum in left half  ` `        ``b) Maximum subarray sum in right half  ` `        ``c) Maximum subarray sum such that the  ` `           ``subarray crosses the midpoint */` `    ``return` `max(maxSubArraySum(``\$arr``, ``\$l``, ``\$m``),  ` `               ``maxSubArraySum(``\$arr``, ``\$m` `+ 1, ``\$h``),  ` `               ``maxCrossingSum(``\$arr``, ``\$l``, ``\$m``, ``\$h``));  ` `}  ` ` `  `// Driver Code ` `\$arr` `= ``array``(2, 3, 4, 5, 7);  ` `\$n` `= ``count``(``\$arr``);  ` `\$max_sum` `= maxSubArraySum(``\$arr``, 0, ``\$n` `- 1);  ` `echo` `"Maximum contiguous sum is "` `. ``\$max_sum``;  ` ` `  `// This code is contributed by rathbhupendra, Aadil ` `?> `

Output :

```Maximum contiguous sum is 21
```

Time Complexity: maxSubArraySum() is a recursive method and time complexity can be expressed as following recurrence relation.
T(n) = 2T(n/2) + Θ(n)
The above recurrence is similar to Merge Sort and can be solved either using Recurrence Tree method or Master method. It falls in case II of Master Method and solution of the recurrence is Θ(nLogn).

The Kadane’s Algorithm for this problem takes O(n) time. Therefore the Kadane’s algorithm is better than the Divide and Conquer approach, but this problem can be considered as a good example to show power of Divide and Conquer. The above simple approach where we divide the array in two halves, reduces the time complexity from O(n^2) to O(nLogn).