Number of subarrays having sum exactly equal to k

Given an unsorted array of integers, find the number of subarrays having sum exactly equal to a given number k.

Examples:

Input : arr[] = {10, 2, -2, -20, 10}, 
        k = -10
Output : 3
Subarrays: arr[0...3], arr[1...4], arr[3..4]
have sum exactly equal to -10.

Input : arr[] = {9, 4, 20, 3, 10, 5},
            k = 33
Output : 2
Subarrays : arr[0...2], arr[2...4] have sum
exactly equal to 33.

A simple solution is to traverse all the subarrays and calculate their sum. If sum is equal to the required sum then increment the count of subarrays. Print final count of subarrays.

An efficient solution is while traversing the array, store sum so far in currsum. Also maintain count of different values of currsum in a map. If value of currsum is equal to desired sum at any instance increment count of subarrays by one. The value of currsum exceeds desired sum by currsum – sum. If this value is removed from currsum then desired sum can be obtained. From the map find number of subarrays previously found having sum equal to currsum-sum. Excluding all those subarrays from current subarray, gives new subarrays having desired sum. So increase count by the number of such subarrays. Note that when currsum is equal to desired sum then also check number of subarrays previously having sum equal to 0. Excluding those subarrays from current subarray gives new subarrays having desired sum. Increase count by the number of subarrays having sum 0 in that case.

C++

filter_none

edit
close

play_arrow

link
brightness_4
code

// C++ program to find number of subarrays
// with sum exactly equal to k.
#include <bits/stdc++.h>
using namespace std;
  
// Function to find number of subarrays 
// with sum exactly equal to k.
int findSubarraySum(int arr[], int n, int sum)
{
    // STL map to store number of subarrays
    // starting from index zero having 
    // particular value of sum.
    unordered_map<int, int> prevSum;
  
    int res = 0;
  
    // Sum of elements so far.
    int currsum = 0;
  
    for (int i = 0; i < n; i++) {
  
        // Add current element to sum so far.
        currsum += arr[i];
  
        // If currsum is equal to desired sum,
        // then a new subarray is found. So
        // increase count of subarrays.
        if (currsum == sum) 
            res++;        
  
        // currsum exceeds given sum by currsum 
        //  - sum. Find number of subarrays having 
        // this sum and exclude those subarrays
        // from currsum by increasing count by 
        // same amount.
        if (prevSum.find(currsum - sum) != 
                                  prevSum.end()) 
            res += (prevSum[currsum - sum]);
          
  
        // Add currsum value to count of 
        // different values of sum.
        prevSum[currsum]++;
    }
  
    return res;
}
  
int main()
{
    int arr[] = { 10, 2, -2, -20, 10 };
    int sum = -10;
    int n = sizeof(arr) / sizeof(arr[0]);
    cout << findSubarraySum(arr, n, sum);
    return 0;
}

chevron_right


Java

filter_none

edit
close

play_arrow

link
brightness_4
code

// Java program to find number of subarrays 
// with sum exactly equal to k. 
import java.util.HashMap;
import java.util.Map;
  
public class GfG{
      
    // Function to find number of subarrays  
    // with sum exactly equal to k. 
    static int findSubarraySum(int arr[], int n, int sum) 
    
        // HashMap to store number of subarrays 
        // starting from index zero having  
        // particular value of sum. 
        HashMap <Integer, Integer> prevSum = new HashMap<>(); 
        
        int res = 0
        
        // Sum of elements so far. 
        int currsum = 0
        
        for (int i = 0; i < n; i++) { 
        
            // Add current element to sum so far. 
            currsum += arr[i]; 
        
            // If currsum is equal to desired sum, 
            // then a new subarray is found. So 
            // increase count of subarrays. 
            if (currsum == sum)  
                res++;         
        
            // currsum exceeds given sum by currsum  
            //  - sum. Find number of subarrays having  
            // this sum and exclude those subarrays 
            // from currsum by increasing count by  
            // same amount. 
            if (prevSum.containsKey(currsum - sum))  
                res += prevSum.get(currsum - sum); 
                
        
            // Add currsum value to count of  
            // different values of sum. 
            Integer count = prevSum.get(currsum);
            if (count == null)
                prevSum.put(currsum, 1);
            else
                prevSum.put(currsum, count+1); 
        
        
        return res; 
    
      
     public static void main(String []args){
          
        int arr[] = { 10, 2, -2, -20, 10 }; 
        int sum = -10
        int n = arr.length;
        System.out.println(findSubarraySum(arr, n, sum));
     }
}
       
// This code is contributed by Rituraj Jain

chevron_right


Python3

filter_none

edit
close

play_arrow

link
brightness_4
code

# Python3 program to find the number of 
# subarrays with sum exactly equal to k. 
from collections import defaultdict
  
# Function to find number of subarrays  
# with sum exactly equal to k. 
def findSubarraySum(arr, n, Sum): 
   
    # Dictionary to store number of subarrays 
    # starting from index zero having  
    # particular value of sum. 
    prevSum = defaultdict(lambda : 0)
    
    res = 0 
    
    # Sum of elements so far. 
    currsum = 0 
    
    for i in range(0, n):  
    
        # Add current element to sum so far. 
        currsum += arr[i] 
    
        # If currsum is equal to desired sum, 
        # then a new subarray is found. So 
        # increase count of subarrays. 
        if currsum == Sum:  
            res += 1         
    
        # currsum exceeds given sum by currsum  - sum.
        # Find number of subarrays having  
        # this sum and exclude those subarrays 
        # from currsum by increasing count by  
        # same amount. 
        if (currsum - Sum) in prevSum:
            res += prevSum[currsum - Sum
            
    
        # Add currsum value to count of  
        # different values of sum. 
        prevSum[currsum] += 1 
       
    return res 
   
if __name__ == "__main__":
  
    arr =  [10, 2, -2, -20, 10]  
    Sum = -10 
    n = len(arr) 
    print(findSubarraySum(arr, n, Sum)) 
      
# This code is contributed by Rituraj Jain
  

chevron_right


C#

filter_none

edit
close

play_arrow

link
brightness_4
code

// C# program to find number of subarrays 
// with sum exactly equal to k.
using System;
using System.Collections.Generic;
  
class GFG 
{
    // Function to find number of subarrays 
    // with sum exactly equal to k.
    public static int findSubarraySum(int[] arr, 
                                   int n, int sum)
    {
          
        // HashMap to store number of subarrays 
        // starting from index zero having 
        // particular value of sum.
        Dictionary <int, int> prevSum = new Dictionary<int, int>();
          
        int res = 0;
          
        // Sum of elements so far
        int currsum = 0;
          
        for (int i = 0; i < n; i++)
        {
              
            // Add current element to sum so far.
            currsum += arr[i];
              
            // If currsum is equal to desired sum, 
            // then a new subarray is found. So 
            // increase count of subarrays.
            if (currsum == sum)
                res++;
              
            // currsum exceeds given sum by currsum 
            // - sum. Find number of subarrays having 
            // this sum and exclude those subarrays 
            // from currsum by increasing count by 
            // same amount.
            if (prevSum.ContainsKey(currsum - sum))
                res += prevSum[currsum - sum];
              
            // Add currsum value to count of 
            // different values of sum.
            if (!prevSum.ContainsKey(currsum))
                prevSum.Add(currsum, 1);
            else
            {
                int count = prevSum[currsum];
                prevSum[currsum] = count + 1;
            }
        }
        return res;
    }
      
    // Driver Code
    public static void Main()
    {
        int[] arr = {10, 2, -2, -20, 10};
        int sum = -10;
        int n = arr.Length;
        Console.Write(findSubarraySum(arr, n, sum));
    }
}
  
// This code is contributed by
// sanjeev2552

chevron_right


Output:

3

Time Complexity: O(n)
Auxiliary Space: O(n)



My Personal Notes arrow_drop_up

A Programmer and A Machine learning Enthusiast

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.



Improved By : rituraj_jain, sanjeev2552



Article Tags :
Practice Tags :


20


Please write to us at contribute@geeksforgeeks.org to report any issue with the above content.