Open In App

Count Subarrays having Sum K

Last Updated : 26 Dec, 2024
Comments
Improve
Suggest changes
Like Article
Like
Report

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

Examples: 

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

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

Input : arr[] = [1, 3, 5], k = 2
Output : 0
Explanation: No subarrays with 0 sum.

[Naive Approach] Using Nested Loop - O(n^2) Time and O(1) Space

A simple solution is to traverse all the subarrays and calculate their sum. If the sum is equal to the given number k, then increment the count of subarrays.

C++
// C++ program to count subarrays having sum K
// using nested loop
#include <iostream>
#include <vector>
using namespace std;

int countSubarrays(vector<int>& arr, int k) {
    int res = 0;

    // Pick a starting point of the subarray
    for (int s = 0; s < arr.size(); s++) {       
        int sum = 0; 
      
        // Pick an ending point
        for (int e = s; e < arr.size(); e++) {
            sum += arr[e];
            if (sum == k)
                res++;
        }
    }

    return res;
}

int main() {
    vector<int> arr = {10, 2, -2, -20, 10};
    int k = -10;
    cout << countSubarrays(arr, k);
    return 0;
}
C
// C program to count subarrays having sum K
// using nested loop
#include <stdio.h>

int countSubarrays(int arr[], int n, int k) {
    int res = 0;

    // Pick a starting point of the subarray
    for (int s = 0; s < n; s++) {
        int sum = 0;

        // Pick an ending point
        for (int e = s; e < n; e++) {
            sum += arr[e];
            if (sum == k)
                res++;
        }
    }

    return res;
}

int main() {
    int arr[] = {10, 2, -2, -20, 10};
    int k = -10;
    int n = sizeof(arr) / sizeof(arr[0]);
    printf("%d", countSubarrays(arr, n, k));
    return 0;
}
Java
// Java program to count subarrays having sum K
// using nested loop
import java.util.*;

class GfG {
    static int countSubarrays(int[] arr, int k) {
        int res = 0;

        // Pick a starting point of the subarray
        for (int s = 0; s < arr.length; s++) {
            int sum = 0;

            // Pick an ending point
            for (int e = s; e < arr.length; e++) {
                sum += arr[e];
                if (sum == k)
                    res++;
            }
        }

        return res;
    }

    public static void main(String[] args) {
        int[] arr = {10, 2, -2, -20, 10};
        int k = -10;
        System.out.println(countSubarrays(arr, k));
    }
}
Python
# Python program to count subarrays having sum K
# using nested loop

def countSubarrays(arr, k):
    res = 0

    # Pick a starting point of the subarray
    for s in range(len(arr)):
        sum = 0

        # Pick an ending point
        for e in range(s, len(arr)):
            sum += arr[e]
            if sum == k:
                res += 1

    return res

if __name__ == "__main__":
    arr = [10, 2, -2, -20, 10]
    k = -10
    print(countSubarrays(arr, k))
C#
// C# program to count subarrays having sum K
// using nested loop
using System;

class GfG {
    static int countSubarrays(int[] arr, int k) {
        int res = 0;

        // Pick a starting point of the subarray
        for (int s = 0; s < arr.Length; s++) {
            int sum = 0;

            // Pick an ending point
            for (int e = s; e < arr.Length; e++) {
                sum += arr[e];
                if (sum == k)
                    res++;
            }
        }

        return res;
    }

    static void Main(string[] args) {
        int[] arr = { 10, 2, -2, -20, 10 };
        int k = -10;
        Console.WriteLine(countSubarrays(arr, k));
    }
}
JavaScript
// JavaScript program to count subarrays having sum K
// using nested loop

function countSubarrays(arr, k) {
    let res = 0;

    // Pick a starting point of the subarray
    for (let s = 0; s < arr.length; s++) {
        let sum = 0;

        // Pick an ending point
        for (let e = s; e < arr.length; e++) {
            sum += arr[e];
            if (sum === k)
                res++;
        }
    }

    return res;
}

// Driver Code
const arr = [10, 2, -2, -20, 10];
const k = -10;
console.log(countSubarrays(arr, k));

Output
3

[Expected Approach] Using Hash Map and Prefix Sum - O(n) Time and O(n) Space

If you take a closer look at this problem, this is mainly an extension of Subarray with given sum.

The idea is to use a Hash Map to store the count of every prefix sum of the array. For each index i, with a current prefix sum currSum, we check if (currSum – k) exists in the map. If it does, it indicates the presence of a subarray ending at i with the given sum k. In such cases, we increment the result with the count of (currSum - k) stored in hash map.



C++
// C++ program to count subarrays having sum K
// using Hash Map

#include <iostream>
#include <vector>
#include <unordered_map>
using namespace std;

// Function to find number of subarrays with
// sum as k
int countSubarrays(vector<int> &arr, int k) {
  
    // unordered_map to store prefix sums frequencies
    unordered_map<int, int> prefixSums;
  
    int res = 0;
    int currSum = 0;

    for (int i = 0; i < arr.size(); 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 == k)
            res++;

        // Check if the difference exists in the prefixSums map.
        if (prefixSums.find(currSum - k) != prefixSums.end())
            res += prefixSums[currSum - k];

        // Add currSum to the set of prefix sums.
        prefixSums[currSum]++;
    }

    return res;
}

int main() {
    vector<int> arr = {10, 2, -2, -20, 10};
    int k = -10;
    cout << countSubarrays(arr, k);
    return 0;
}
Java
// Java program to count subarrays having sum K
// using Hash Map
import java.util.*;

class GfG {
    // Function to find number of subarrays with sum as k
    static int countSubarrays(int[] arr, int k) {

        // HashMap to store prefix sums frequencies
        Map<Integer, Integer> prefixSums = new HashMap<>();
        int res = 0;
        int currSum = 0;

        for (int i = 0; i < arr.length; i++) {
            // Add current element to sum so far.
            currSum += arr[i];

            // If currSum is equal to desired sum, then a new subarray is found.
            if (currSum == k)
                res++;

            // Check if the difference exists in the prefixSums map.
            if (prefixSums.containsKey(currSum - k))
                res += prefixSums.get(currSum - k);

            // Add currSum to the set of prefix sums.
            prefixSums.put(currSum, prefixSums.getOrDefault(currSum, 0) + 1);
        }

        return res;
    }

    public static void main(String[] args) {
        int[] arr = {10, 2, -2, -20, 10};
        int k = -10;
        System.out.println(countSubarrays(arr, k));
    }
}
Python
# Python program to count subarrays having sum K
# using Hash Map

def countSubarrays(arr, k):
    # Dictionary to store prefix sums frequencies
    prefixSums = {}
    res = 0
    currSum = 0

    for val in arr:
        # Add current element to sum so far
        currSum += val

        # If currSum is equal to desired sum, then a new subarray is found
        if currSum == k:
            res += 1

        # Check if the difference exists in the prefixSums dictionary
        if currSum - k in prefixSums:
            res += prefixSums[currSum - k]

        # Add currSum to the dictionary of prefix sums
        prefixSums[currSum] = prefixSums.get(currSum, 0) + 1

    return res

if __name__ == "__main__":
    arr = [10, 2, -2, -20, 10]
    k = -10
    print(countSubarrays(arr, k))
C#
// C# program to count subarrays having sum K
// using Hash Map
using System;
using System.Collections.Generic;

class GfG {
    // Function to find number of subarrays with sum as k
    static int countSubarrays(int[] arr, int k) {
        // Dictionary to store prefix sums frequencies
        Dictionary<int, int> prefixSums = new Dictionary<int, int>();
        int res = 0;
        int currSum = 0;

        for (int i = 0; i < arr.Length; i++) {
            // Add current element to sum so far
            currSum += arr[i];

            // If currSum is equal to desired sum, then a new subarray is found
            if (currSum == k)
                res++;

            // Check if the difference exists in the prefixSums dictionary
            if (prefixSums.ContainsKey(currSum - k))
                res += prefixSums[currSum - k];

            // Add currSum to the dictionary of prefix sums
            if (!prefixSums.ContainsKey(currSum))
                prefixSums[currSum] = 0;
            prefixSums[currSum]++;
        }

        return res;
    }

    static void Main(string[] args) {
        int[] arr = { 10, 2, -2, -20, 10 };
        int k = -10;
        Console.WriteLine(countSubarrays(arr, k));
    }
}
JavaScript
// JavaScript program to count subarrays having sum K
// using Hash Map

function countSubarrays(arr, k) {

    // Map to store prefix sums frequencies
    const prefixSums = new Map();
    let res = 0;
    let currSum = 0;

    for (let val of arr) {
        // Add current element to sum so far
        currSum += val;

        // If currSum is equal to desired sum, then a new subarray is found
        if (currSum === k)
            res++;

        // Check if the difference exists in the prefixSums map
        if (prefixSums.has(currSum - k))
            res += prefixSums.get(currSum - k);

        // Add currSum to the map of prefix sums
        prefixSums.set(currSum, (prefixSums.get(currSum) || 0) + 1);
    }

    return res;
}

// Driver Code
const arr = [10, 2, -2, -20, 10];
const k = -10;
console.log(countSubarrays(arr, k));

Output
3


Next Article
Practice Tags :

Similar Reads