Open In App

Longest alternating subsequence which has maximum sum of elements

Given a list of length N with positive and negative integers. The task is to choose the longest alternating subsequence of the given sequence (i.e. the sign of each next element is the opposite of the sign of the current element). Among all such subsequences, we have to choose one which has the maximum sum of elements and display that sum.

Examples:



Input: list = [-2 10 3 -8 -4 -1 5 -2 -3 1] 
Output: 11 
Explanation: 
The largest subsequence with the greatest sum is [-2 10 -1 5 -2 1] with length 6.

Input: list=[12 4 -5 7 -9] 
Output:
Explanation: 
The largest subsequence with greatest sum is [12 -5 7 -9] with length 4.



Approach: The solution can be reached by the following approach:-

Lets take an example, we have a list [1, 2, 3, -2, -5, 1, -7, -1].

  1. In traversing this list length-1 times, we are getting 1, 2, 3 with the same sign so we will append greatest of these (i.e 3) to another list named large here. 
    Hence large=[3]
  2. Now -2 and -5 have the same sign so we will append -2 to another List. 
    large=[3, -2]
  3. Now, the sign of 1 and -7 are opposite, so we will append 1 to large. 
    large=[3, -2, 1]
  4. For -7, -1 signs are same, Hence append -1 to large. 
    large=[3, -2, 1, -1]
  5. Calculate the sum = 3 – 2 + 1 – 1 = 1

Below is the implementation of the above approach:




// C++ implementation to find the
// longest alternating subsequence
// which has the maximum sum
#include<bits/stdc++.h>
using namespace std;
 
int calculateMaxSum(int n, int li[])
{
     
    // Creating a temporary list ar to
    // every time store same sign element
    // to calculate maximum element from
    // that list ar
    vector<int> ar;
     
    // Appending 1st element of list li
    // to the ar
    ar.push_back(li[0]);
     
    // Creating list to store maximum
    // values
    vector<int> large;
 
    for(int j = 0; j < n - 1; j++)
    {
        
       // If both number are positive
       // then append (j + 1)th element
       // to temporary list ar
       if(li[j] > 0 and li[j + 1] > 0)
       {
           ar.push_back(li[j + 1]);
       }
       else if(li[j] > 0 and li[j + 1] < 0)
       {
            
           // If opposite elements found
           // then append maximum element
           // to large list
           large.push_back(*max_element(ar.begin(),
                                        ar.end()));
                                         
           // Empty ar list to re-append
           // next elements
           ar.clear();
           ar.push_back(li[j + 1]);
       }
       else if(li[j] < 0 and li[j + 1] > 0)
       {
            
           // If opposite elements found
           // then append maximum element
           // to large list
           large.push_back(*max_element(ar.begin(),
                                        ar.end()));
            
           // Empty ar list to re-append
           // next elements
           ar.clear();
           ar.push_back(li[j + 1]);
       }
       else
       {
           // If both number are negative
           // then append (j + 1)th element
           // to temporary list ar
           ar.push_back(li[j + 1]);
       }
    }
     
    // The final Maximum element in ar list
    // also needs to be appended to large list
    large.push_back(*max_element(ar.begin(),
                                 ar.end()));
     
    // Returning the sum of all elements
    // from largest elements list with
    // largest alternating subsequence size
    int sum = 0;
    for(int i = 0; i < large.size(); i++)
       sum += large[i];
    return sum;
}
     
// Driver code
int main()
{
    int list[] = { -2, 8, 3, 8, -4, -15,
                    5, -2, -3, 1 };
    int N = sizeof(list) / sizeof(list[0]);
 
    cout << (calculateMaxSum(N, list));
}
 
// This code is contributed by Bhupendra_Singh




// Java implementation to find the
// longest alternating subsequence
// which has the maximum sum
import java.util.*;
 
class GFG{
 
static int calculateMaxSum(int n, int li[])
{
     
    // Creating a temporary list ar to
    // every time store same sign element
    // to calculate maximum element from
    // that list ar
    Vector<Integer> ar = new Vector<>();
     
    // Appending 1st element of list li
    // to the ar
    ar.add(li[0]);
     
    // Creating list to store maximum
    // values
    Vector<Integer> large = new Vector<>();
 
    for(int j = 0; j < n - 1; j++)
    {
         
        // If both number are positive
        // then append (j + 1)th element
        // to temporary list ar
        if(li[j] > 0 && li[j + 1] > 0)
        {
            ar.add(li[j + 1]);
        }
        else if(li[j] > 0 && li[j + 1] < 0)
        {
                 
            // If opposite elements found
            // then append maximum element
            // to large list
            large.add(Collections.max(ar));
                                             
            // Empty ar list to re-append
            // next elements
            ar.clear();
            ar.add(li[j + 1]);
        }
        else if(li[j] < 0 && li[j + 1] > 0)
        {
                 
            // If opposite elements found
            // then append maximum element
            // to large list
            large.add(Collections.max(ar));
                 
            // Empty ar list to re-append
            // next elements
            ar.clear();
            ar.add(li[j + 1]);
        }
        else
        {
            // If both number are negative
            // then append (j + 1)th element
            // to temporary list ar
            ar.add(li[j + 1]);
        }
    }
     
    // The final Maximum element in ar list
    // also needs to be appended to large list
    large.add(Collections.max(ar));
     
    // Returning the sum of all elements
    // from largest elements list with
    // largest alternating subsequence size
    int sum = 0;
    for(int i = 0; i < large.size(); i++)
        sum += (int)large.get(i);
         
    return sum;
}
 
// Driver code
public static void main(String args[])
{
    int list[] = { -2, 8, 3, 8, -4, -15,
                    5, -2, -3, 1 };
    int N = (list.length);
     
    System.out.print(calculateMaxSum(N, list));
}
}
 
// This code is contributed by Stream_Cipher




# Python3 implementation to find the
# longest alternating subsequence
# which has the maximum sum
 
def calculateMaxSum(n, li):
    # Creating a temporary list ar to every
    # time store same sign element to
    # calculate maximum element from
    # that list ar
    ar =[]
     
    # Appending 1st element of list li
    # to the ar
    ar.append(li[0])
     
    # Creating list to store maximum
    # values
    large =[]
     
    for j in range(0, n-1):
         
        # If both number are positive
        # then append (j + 1)th element
        # to temporary list ar
        if(li[j]>0 and li[j + 1]>0):
            ar.append(li[j + 1])
        elif(li[j]>0 and li[j + 1]<0):
             
            # If opposite elements found
            # then append maximum element
            # to large list
            large.append(max(ar))
             
            # Empty ar list to re-append
            # next elements 
            ar =[]
            ar.append(li[j + 1])
        elif(li[j]<0 and li[j + 1]>0):
             
            # If opposite elements found
            # then append maximum element
            # to large list
            large.append(max(ar))
             
            # Empty ar list to re-append
            # next elements
            ar =[]
            ar.append(li[j + 1])
        else:
            # If both number are negative
            # then append (j + 1)th element
            # to temporary list ar
            ar.append(li[j + 1])
             
    # The final Maximum element in ar list
    # also needs to be appended to large list
    large.append(max(ar))
     
    # returning the sum of all elements
    # from largest elements list with
    # largest alternating subsequence size
    return sum(large)
 
 
# Driver code
list =[-2, 8, 3, 8, -4, -15, 5, -2, -3, 1]
N = len(list)
 
print(calculateMaxSum(N, list))




// C# implementation to find the
// longest alternating subsequence
// which has the maximum sum
using System;
using System.Collections.Generic;
 
class GFG{
 
static int find_max(List<int> ar)
{
    int mx = -1000000;
    foreach(var i in ar)
    {
        if(i > mx)
           mx = i;
    }
    return mx;
}
 
static int calculateMaxSum(int n, int []li)
{
     
    // Creating a temporary list ar to
    // every time store same sign element
    // to calculate maximum element from
    // that list ar
    List<int> ar = new List<int>();
     
    // Appending 1st element of list li
    // to the ar
    ar.Add(li[0]);
     
    // Creating list to store maximum
    // values
    List<int> large = new List<int>();
 
    for(int j = 0; j < n - 1; j++)
    {
         
        // If both number are positive
        // then append (j + 1)th element
        // to temporary list ar
        if(li[j] > 0 && li[j + 1] > 0)
        {
            ar.Add(li[j + 1]);
        }
        else if(li[j] > 0 && li[j + 1] < 0)
        {
                 
            // If opposite elements found
            // then append maximum element
            // to large list
            large.Add(find_max(ar));
                                             
            // Empty ar list to re-append
            // next elements
            ar.Clear();
            ar.Add(li[j + 1]);
        }
        else if(li[j] < 0 && li[j + 1] > 0)
        {
                 
            // If opposite elements found
            // then append maximum element
            // to large list
            large.Add(find_max(ar));
                 
            // Empty ar list to re-append
            // next elements
            ar.Clear();
            ar.Add(li[j + 1]);
        }
        else
        {
             
            // If both number are negative
            // then append (j + 1)th element
            // to temporary list ar
            ar.Add(li[j + 1]);
        }
    }
     
    // The final Maximum element in ar list
    // also needs to be appended to large list
    large.Add(find_max(ar));
     
    // Returning the sum of all elements
    // from largest elements list with
    // largest alternating subsequence size
    int sum = 0;
    foreach(var i in large)
    {
        sum += i;
    }
    return sum;
}
 
// Driver code
public static void Main()
{
    int []list = { -2, 8, 3, 8, -4, -15,
                    5, -2, -3, 1 };
    int N = (list.Length);
     
    Console.WriteLine(calculateMaxSum(N, list));
}
}
 
// This code is contributed by Stream_Cipher   




<script>
    // Javascript implementation to find the
    // longest alternating subsequence
    // which has the maximum sum
     
    function find_max(ar)
    {
        let mx = -1000000;
        for(let i = 0; i < ar.length; i++)
        {
            if(ar[i] > mx)
               mx = ar[i];
        }
        return mx;
    }
 
    function calculateMaxSum(n, li)
    {
 
        // Creating a temporary list ar to
        // every time store same sign element
        // to calculate maximum element from
        // that list ar
        let ar = [];
 
        // Appending 1st element of list li
        // to the ar
        ar.push(li[0]);
 
        // Creating list to store maximum
        // values
        let large = [];
 
        for(let j = 0; j < n - 1; j++)
        {
 
            // If both number are positive
            // then append (j + 1)th element
            // to temporary list ar
            if(li[j] > 0 && li[j + 1] > 0)
            {
                ar.push(li[j + 1]);
            }
            else if(li[j] > 0 && li[j + 1] < 0)
            {
 
                // If opposite elements found
                // then append maximum element
                // to large list
                large.push(find_max(ar));
 
                // Empty ar list to re-append
                // next elements
                ar = [];
                ar.push(li[j + 1]);
            }
            else if(li[j] < 0 && li[j + 1] > 0)
            {
 
                // If opposite elements found
                // then append maximum element
                // to large list
                large.push(find_max(ar));
 
                // Empty ar list to re-append
                // next elements
                ar = [];
                ar.push(li[j + 1]);
            }
            else
            {
 
                // If both number are negative
                // then append (j + 1)th element
                // to temporary list ar
                ar.push(li[j + 1]);
            }
        }
 
        // The final Maximum element in ar list
        // also needs to be appended to large list
        large.push(find_max(ar));
 
        // Returning the sum of all elements
        // from largest elements list with
        // largest alternating subsequence size
        let sum = 0;
        for(let i = 0; i < large.length; i++)
        {
            sum += large[i];
        }
        return sum;
    }
     
    let list = [ -2, 8, 3, 8, -4, -15, 5, -2, -3, 1 ];
    let N = (list.length);
       
    document.write(calculateMaxSum(N, list));
     
</script>

Output: 
6

Time Complexity:O(N2)
Auxiliary Space: O(N)


Article Tags :