Maximum sum from three arrays such that picking elements consecutively from same is not allowed

Given three arrays A[], B[], and C[] of N integers. We can choose N elements from this array such that for every index i only one element can be chosen from this array i.e. either A[i], B[i], or C[i], and no two consecutive elements can be chosen from the same array. The task is to print the maximum sum of numbers that we can make by choosing elements from these arrays.Â
Examples:Â
Input: a[] = {10, 20, 30}, b[] = {40, 50, 60}, c[] = {70, 80, 90}Â
Output: 210Â
70 + 50 + 90 = 210Input: a[] = {6, 8, 2, 7, 4, 2, 7}, b[] = {7, 8, 5, 8, 6, 3, 5}, c[] = {8, 3, 2, 6, 8, 4, 1}Â
Output: 46Â
Choose elements from C, A, B, A, C, B and A.Â
Approach: The above problem can be solved using Dynamic Programming. Let dp[i][j] be considered the maximum sum till i if an element from j-th array is chosen. We can select an element from any array for the first index, but later on recursively we can choose an element only from the rest two arrays for the next step. The maximum sum returned by all of the combinations will be our answer. Use memoization to avoid repetitive and multiple same-function calls.Â
Below is the implementation of the above approach:Â
C++
// C++ implementation of the approach#include <bits/stdc++.h>using namespace std;const int N = 3;Â
// Function to return the maximum sumint FindMaximumSum(int ind, int kon, int a[], int b[],                   int c[], int n, int dp[][N]){Â
    // Base case    if (ind == n)        return 0;Â
    // Already visited    if (dp[ind][kon] != -1)        return dp[ind][kon];    int ans = -1e9 + 5;Â
    // If the element has been taken    // from first array in previous step    if (kon == 0) {        ans = max(ans, b[ind] + FindMaximumSum(ind + 1,                                               1, a, b,                                               c, n, dp));        ans = max(ans, c[ind] + FindMaximumSum(ind + 1,                                               2, a, b,                                               c, n, dp));    }Â
    // If the element has been taken    // from second array in previous step    else if (kon == 1) {        ans = max(ans, a[ind] + FindMaximumSum(ind + 1,                                               0, a, b,                                               c, n, dp));        ans = max(ans, c[ind] + FindMaximumSum(ind + 1,                                               2, a, b,                                               c, n, dp));    }Â
    // If the element has been taken    // from third array in previous step    else if (kon == 2) {        ans = max(ans, a[ind] + FindMaximumSum(ind + 1,                                               1, a, b,                                               c, n, dp));        ans = max(ans, b[ind] + FindMaximumSum(ind + 1,                                               0, a, b,                                               c, n, dp));    }Â
    return dp[ind][kon] = ans;}Â
// Driver codeint main(){Â Â Â Â int a[] = { 6, 8, 2, 7, 4, 2, 7 };Â Â Â Â int b[] = { 7, 8, 5, 8, 6, 3, 5 };Â Â Â Â int c[] = { 8, 3, 2, 6, 8, 4, 1 };Â Â Â Â int n = sizeof(a) / sizeof(a[0]);Â Â Â Â int dp[n][N];Â Â Â Â memset(dp, -1, sizeof dp);Â
    // Pick element from first array    int x = FindMaximumSum(0, 0, a, b, c, n, dp);Â
    // Pick element from second array    int y = FindMaximumSum(0, 1, a, b, c, n, dp);Â
    // Pick element from third array    int z = FindMaximumSum(0, 2, a, b, c, n, dp);Â
    // Print the maximum of them    cout << max(x, max(y, z));Â
    return 0;} |
Java
// Java program for the above approachÂ
class GFG {     static int N = 3;  // Function to return the maximum sumstatic int FindMaximumSum(int ind, int kon, int a[],               int b[], int c[], int n, int dp[][])                    {    // Base case    if (ind == n)        return 0;      // Already visited    if (dp[ind][kon] != -1)        return dp[ind][kon];    int ans = (int) (-1e9 + 5);      // If the element has been taken    // from first array in previous step    if (kon == 0) {        ans = Math.max(ans, b[ind] +               FindMaximumSum(ind + 1,                  1, a, b,c, n, dp));                                                                                                        ans = Math.max(ans, c[ind] +               FindMaximumSum(ind + 1,                  2, a, b,c, n, dp));                                                                                            }      // If the element has been taken    // from second array in previous step    else if (kon == 1) {        ans = Math.max(ans, a[ind] +               FindMaximumSum(ind + 1,                 0, a, b, c, n, dp));                                                                                         ans = Math.max(ans, c[ind] +               FindMaximumSum(ind + 1,                  2, a, b, c, n, dp));                                                                                               }      // If the element has been taken    // from third array in previous step    else if (kon == 2) {        ans = Math.max(ans, a[ind] +               FindMaximumSum(ind + 1,                 1, a, b, c, n, dp));                                                                                                        ans = Math.max(ans, b[ind] +               FindMaximumSum(ind + 1,                 0, a, b, c, n, dp));                                                                                                    }      return dp[ind][kon] = ans;}  // Driver codepublic static void main(String[] args) {Â
    int a[] = { 6, 8, 2, 7, 4, 2, 7 };    int b[] = { 7, 8, 5, 8, 6, 3, 5 };    int c[] = { 8, 3, 2, 6, 8, 4, 1 };    int n = a.length;    int dp[][] = new int[n][N];Â
    for(int i = 0; i < n; i++) {Â
        for(int j = 0; j < N; j++) {            dp[i][j] =- 1;        }    }      // Pick element from first array    int x = FindMaximumSum(0, 0, a, b, c, n, dp);      // Pick element from second array    int y = FindMaximumSum(0, 1, a, b, c, n, dp);      // Pick element from third array    int z = FindMaximumSum(0, 2, a, b, c, n, dp);      // Print the maximum of them    System.out.println(Math.max(x, Math.max(y, z)));      }}// This code has been contributed// by 29AjayKumar |
Python3
# Python3 implementation of the approach Â
# Function to return the maximum sum def FindMaximumSum(ind, kon, a, b, c, n, dp): Â
    # Base case     if ind == n:        return 0Â
    # Already visited     if dp[ind][kon] != -1:        return dp[ind][kon]          ans = -10 ** 9 + 5Â
    # If the element has been taken     # from first array in previous step     if kon == 0:         ans = max(ans, b[ind] +                  FindMaximumSum(ind + 1, 1,                                  a, b, c, n, dp))         ans = max(ans, c[ind] +                  FindMaximumSum(ind + 1, 2,                                  a, b, c, n, dp))          # If the element has been taken     # from second array in previous step     elif kon == 1:         ans = max(ans, a[ind] +                  FindMaximumSum(ind + 1, 0,                                  a, b, c, n, dp))         ans = max(ans, c[ind] +                  FindMaximumSum(ind + 1, 2,                                  a, b, c, n, dp))          # If the element has been taken     # from third array in previous step     elif kon == 2:         ans = max(ans, a[ind] +                  FindMaximumSum(ind + 1, 1,                                  a, b, c, n, dp))         ans = max(ans, b[ind] +                  FindMaximumSum(ind + 1, 0,                                  a, b, c, n, dp))          dp[ind][kon] = ans    return ansÂ
# Driver code if __name__ == "__main__": Â Â Â Â Â Â Â Â Â N = 3Â Â Â Â a = [6, 8, 2, 7, 4, 2, 7] Â Â Â Â b = [7, 8, 5, 8, 6, 3, 5] Â Â Â Â c = [8, 3, 2, 6, 8, 4, 1] Â Â Â Â n = len(a)Â Â Â Â Â Â Â Â Â dp = [[-1 for i in range(N)] Â Â Â Â Â Â Â Â Â Â Â Â Â Â for j in range(n)]Â
    # Pick element from first array     x = FindMaximumSum(0, 0, a, b, c, n, dp) Â
    # Pick element from second array     y = FindMaximumSum(0, 1, a, b, c, n, dp) Â
    # Pick element from third array     z = FindMaximumSum(0, 2, a, b, c, n, dp) Â
    # Print the maximum of them     print(max(x, y, z)) Â
# This code is contributed# by Rituraj Jain |
C#
// C# program for the above approach using System;Â
class GFG {          static int N = 3;          // Function to return the maximum sum     static int FindMaximumSum(int ind, int kon, int []a,                 int []b, int []c, int n, int [,]dp)                              {         // Base case         if (ind == n)             return 0;              // Already visited         if (dp[ind,kon] != -1)             return dp[ind,kon];         int ans = (int) (-1e9 + 5);              // If the element has been taken         // from first array in previous step         if (kon == 0)         {             ans = Math.Max(ans, b[ind] +                 FindMaximumSum(ind + 1,                     1, a, b,c, n, dp));                                                                                                                       ans = Math.Max(ans, c[ind] +                 FindMaximumSum(ind + 1,                     2, a, b,c, n, dp));                                                                                                      }              // If the element has been taken         // from second array in previous step         else if (kon == 1)         {             ans = Math.Max(ans, a[ind] +                 FindMaximumSum(ind + 1,                     0, a, b, c, n, dp));                                                                                                  ans = Math.Max(ans, c[ind] +                 FindMaximumSum(ind + 1,                     2, a, b, c, n, dp));                                                                                                          }              // If the element has been taken         // from third array in previous step         else if (kon == 2)         {             ans = Math.Max(ans, a[ind] +                 FindMaximumSum(ind + 1,                     1, a, b, c, n, dp));                                                                                                                       ans = Math.Max(ans, b[ind] +                 FindMaximumSum(ind + 1,                     0, a, b, c, n, dp));                                                                                                                   }              return dp[ind,kon] = ans;     }          // Driver code     public static void Main()     {              int []a = { 6, 8, 2, 7, 4, 2, 7 };         int []b = { 7, 8, 5, 8, 6, 3, 5 };         int []c = { 8, 3, 2, 6, 8, 4, 1 };         int n = a.Length;         int [,]dp = new int[n,N];              for(int i = 0; i < n; i++)         {                  for(int j = 0; j < N; j++)            {                 dp[i,j] =- 1;             }         }              // Pick element from first array         int x = FindMaximumSum(0, 0, a, b, c, n, dp);              // Pick element from second array         int y = FindMaximumSum(0, 1, a, b, c, n, dp);              // Pick element from third array         int z = FindMaximumSum(0, 2, a, b, c, n, dp);              // Print the maximum of them         Console.WriteLine(Math.Max(x, Math.Max(y, z)));              } } Â
// This code has been contributed by Ryuga |
Javascript
<script>Â
// JavaScript implementation of the approachvar N = 3;Â
// Function to return the maximum sumfunction FindMaximumSum(ind, kon, a, b, c, n, dp){Â
    // Base case    if (ind == n)        return 0;Â
    // Already visited    if (dp[ind][kon] != -1)        return dp[ind][kon];    var ans = -1000000005;Â
    // If the element has been taken    // from first array in previous step    if (kon == 0) {        ans = Math.max(ans, b[ind] + FindMaximumSum(ind + 1,                                               1, a, b,                                               c, n, dp));        ans = Math.max(ans, c[ind] + FindMaximumSum(ind + 1,                                               2, a, b,                                               c, n, dp));    }Â
    // If the element has been taken    // from second array in previous step    else if (kon == 1) {        ans = Math.max(ans, a[ind] + FindMaximumSum(ind + 1,                                               0, a, b,                                               c, n, dp));        ans = Math.max(ans, c[ind] + FindMaximumSum(ind + 1,                                               2, a, b,                                               c, n, dp));    }Â
    // If the element has been taken    // from third array in previous step    else if (kon == 2) {        ans = Math.max(ans, a[ind] + FindMaximumSum(ind + 1,                                               1, a, b,                                               c, n, dp));        ans = Math.max(ans, b[ind] + FindMaximumSum(ind + 1,                                               0, a, b,                                               c, n, dp));    }Â
    return dp[ind][kon] = ans;}Â
// Driver codevar a = [ 6, 8, 2, 7, 4, 2, 7 ];var b = [ 7, 8, 5, 8, 6, 3, 5 ];var c = [ 8, 3, 2, 6, 8, 4, 1 ];var n = a.length;var dp = Array.from(Array(n), ()=> Array(n).fill(-1));// Pick element from first arrayvar x = FindMaximumSum(0, 0, a, b, c, n, dp);// Pick element from second arrayvar y = FindMaximumSum(0, 1, a, b, c, n, dp);// Pick element from third arrayvar z = FindMaximumSum(0, 2, a, b, c, n, dp);// Print the maximum of themdocument.write( Math.max(x, Math.max(y, z)));Â
</script> |
PHP
<?php// PHP implementation of the approach$N = 3;Â
// Function to return the maximum sumfunction FindMaximumSum($ind, $kon, $a,                         $b, $c, $n, $dp){    global $N;         // Base case    if ($ind == $n)        return 0;Â
    // Already visited    if ($dp[$ind][$kon] != -1)        return $dp[$ind][$kon];    $ans = -1e9 + 5;Â
    // If the element has been taken    // from first array in previous step    if ($kon == 0)     {        $ans = max($ans, $b[$ind] +                    FindMaximumSum($ind + 1, 1, $a,                                  $b, $c, $n, $dp));        $ans = max($ans, $c[$ind] +                    FindMaximumSum($ind + 1, 2, $a,                                   $b, $c, $n, $dp));    }Â
    // If the element has been taken    // from second array in previous step    else if ($kon == 1)     {        $ans = max($ans, $a[$ind] +                    FindMaximumSum($ind + 1, 0,                                  $a, $b, $c, $n, $dp));        $ans = max($ans, $c[$ind] +                    FindMaximumSum($ind + 1, 2,                                   $a, $b, $c, $n, $dp));    }Â
    // If the element has been taken    // from third array in previous step    else if ($kon == 2)     {        $ans = max($ans, $a[$ind] +                    FindMaximumSum($ind + 1, 1,                                   $a, $b, $c, $n, $dp));        $ans = max($ans, $b[$ind] +                    FindMaximumSum($ind + 1, 0,                                   $a, $b, $c, $n, $dp));    }Â
    return $dp[$ind][$kon] = $ans;}Â
// Driver code$a = array( 6, 8, 2, 7, 4, 2, 7 );$b = array( 7, 8, 5, 8, 6, 3, 5 );$c = array( 8, 3, 2, 6, 8, 4, 1 );$n = count($a);$dp = array_fill(0, $n, Â Â Â Â Â Â array_fill(0, $N, -1));Â
// Pick element from first array$x = FindMaximumSum(0, 0, $a, $b, Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $c, $n, $dp);Â
// Pick element from second array$y = FindMaximumSum(0, 1, $a, $b, Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $c, $n, $dp);Â
// Pick element from third array$z = FindMaximumSum(0, 2, $a, $b, Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $c, $n, $dp);Â
// Print the maximum of themprint(max($x, max($y, $z)));Â
// This code is contributed by mits?> |
45
Time Complexity: O(N), as we are using recursion with memorization we will avoid the redundant function calls. Where N is the number of elements in the array.
Auxiliary Space: O(N), as we use extra space for the dp matrix. Where N is the number of elements in the array.
Efficient Approach: Using the DP Tabulation method ( Iterative approach )
The approach to solving this problem is the same but the DP tabulation(bottom-up) method is better than Dp + memoization(top-down) because the memoization method needs extra stack space for recursion calls.
Steps:
- Create a DP to store the solution of the subproblems and initialize it with 0.
- Initialize the DP with base cases
- Now Iterate over subproblems to get the value of the current problem from the previous computation of subproblems stored in DP
- At last, find the maximum value in DP and return an answer.
Implementation :
C++
#include <bits/stdc++.h>using namespace std;Â
const int N = 3;Â
// Function to return the maximum sumint FindMaximumSum(int a[], int b[], int c[], int n){Â Â Â Â int dp[n][N];Â Â Â Â memset(dp, 0, sizeof dp);Â
    // Set the first row of dp table    dp[0][0] = a[0];    dp[0][1] = b[0];    dp[0][2] = c[0];Â
    // Iterate over remaining elements    for (int i = 1; i < n; i++) {        dp[i][0] = max(dp[i-1][1], dp[i-1][2]) + a[i];        dp[i][1] = max(dp[i-1][0], dp[i-1][2]) + b[i];        dp[i][2] = max(dp[i-1][0], dp[i-1][1]) + c[i];    }Â
    // Return the maximum sum    return max(dp[n-1][0], max(dp[n-1][1], dp[n-1][2]));}Â
// Driver codeint main(){Â Â Â Â int a[] = {10, 20, 30}, b[] = {40, 50, 60}, c[] = {70, 80, 90} ;Â Â Â Â int n = sizeof(a) / sizeof(a[0]);Â
    // Call the function    cout << FindMaximumSum(a, b, c, n);Â
    return 0;} |
Java
import java.util.Arrays;Â
public class Main {Â
    // Driver Code    public static void main(String[] args)    {        int[] a = { 10, 20, 30 };        int[] b = { 40, 50, 60 };        int[] c = { 70, 80, 90 };        int n = a.length;Â
        // Call the function and        // print the result        System.out.println(FindMaximumSum(a, b, c, n));    }Â
    // Function to return the maximum sum    public static int FindMaximumSum(int[] a, int[] b,                                     int[] c, int n)    {        int[][] dp = new int[n][3];        for (int[] row : dp) {            Arrays.fill(row, 0);        }Â
        // Set the first row of dp table        dp[0][0] = a[0];        dp[0][1] = b[0];        dp[0][2] = c[0];Â
        // Iterate over remaining elements        for (int i = 1; i < n; i++) {            dp[i][0] = Math.max(dp[i - 1][1], dp[i - 1][2])                       + a[i];            dp[i][1] = Math.max(dp[i - 1][0], dp[i - 1][2])                       + b[i];            dp[i][2] = Math.max(dp[i - 1][0], dp[i - 1][1])                       + c[i];        }Â
        // Return the maximum sum        return Math.max(            dp[n - 1][0],            Math.max(dp[n - 1][1], dp[n - 1][2]));    }} |
Python3
import sysÂ
N = 3Â
# Function to return the maximum sumdef find_maximum_sum(a, b, c, n):Â Â Â Â dp = [[0 for i in range(N)] for j in range(n)]Â
    # Set the first row of dp table    dp[0][0] = a[0]    dp[0][1] = b[0]    dp[0][2] = c[0]Â
    # Iterate over remaining elements    for i in range(1, n):        dp[i][0] = max(dp[i-1][1], dp[i-1][2]) + a[i]        dp[i][1] = max(dp[i-1][0], dp[i-1][2]) + b[i]        dp[i][2] = max(dp[i-1][0], dp[i-1][1]) + c[i]Â
    # Return the maximum sum    return max(dp[n-1][0], max(dp[n-1][1], dp[n-1][2]))Â
# Driver codeif __name__ == "__main__":Â Â Â Â a = [10, 20, 30]Â Â Â Â b = [40, 50, 60]Â Â Â Â c = [70, 80, 90]Â Â Â Â n = len(a)Â
    # Call the function    print(find_maximum_sum(a, b, c, n)) |
C#
using System;Â
public class Program {public static int FindMaximumSum(int[] a, int[] b, int[] c, int n){int[,] dp = new int[n, 3];dp[0, 0] = a[0];dp[0, 1] = b[0];dp[0, 2] = c[0]; Â Â Â Â Â Â for (int i = 1; i < n; i++) {Â Â Â Â Â Â Â Â dp[i, 0] = Math.Max(dp[i-1, 1], dp[i-1, 2]) + a[i];Â Â Â Â Â Â Â Â dp[i, 1] = Math.Max(dp[i-1, 0], dp[i-1, 2]) + b[i];Â Â Â Â Â Â Â Â dp[i, 2] = Math.Max(dp[i-1, 0], dp[i-1, 1]) + c[i];Â Â Â Â }Â
    return Math.Max(dp[n-1, 0], Math.Max(dp[n-1, 1], dp[n-1, 2]));}Â
public static void Main(){Â Â Â Â int[] a = {10, 20, 30};Â Â Â Â int[] b = {40, 50, 60};Â Â Â Â int[] c = {70, 80, 90};Â Â Â Â int n = a.Length;Â
    Console.WriteLine(FindMaximumSum(a, b, c, n));}} |
Javascript
function FindMaximumSum(a, b, c, n) {Â Â let dp = [];Â Â for (let i = 0; i < n; i++) {Â Â Â Â dp.push([0, 0, 0]);Â Â }Â
  // Set the first row of dp table  dp[0][0] = a[0];  dp[0][1] = b[0];  dp[0][2] = c[0];Â
  // Iterate over remaining elements  for (let i = 1; i < n; i++) {    dp[i][0] = Math.max(dp[i - 1][1], dp[i - 1][2]) + a[i];    dp[i][1] = Math.max(dp[i - 1][0], dp[i - 1][2]) + b[i];    dp[i][2] = Math.max(dp[i - 1][0], dp[i - 1][1]) + c[i];  }Â
  // Return the maximum sum  return Math.max(dp[n - 1][0], Math.max(dp[n - 1][1], dp[n - 1][2]));}Â
// Driver Codelet a = [10, 20, 30];let b = [40, 50, 60];let c = [70, 80, 90];let n = a.length;Â
// Call the function and print the resultconsole.log(FindMaximumSum(a, b, c, n)); |
210
Time Complexity: O(N)
Auxiliary Space: O(N)
Ready to dive in? Explore our Free Demo Content and join our DSA course, trusted by over 100,000 zambiatek!



