Prefix Sum - The general approach to a contiguous subarray problem.

Introduction


A prefix sum of an array of numbers is the cumulative sum of the array. Using this method, we can easily calculate the sum between two points of the array in constant time. I will be updating this page as and when I come across more prefix sum problems.

1. Find Subarray with given sum


Description

Find if there exists a subarray with a given sum in an unsorted array.

Explanation:

 

2. LeetCode 560 - Subarray Sum equals K


Description:

Find the number of subarrays that exist with a given sum.

Eg:	Input:nums = [1,1,1], k = 2
	Output: 2

Explanation:

    int subarraySum(vector<int>& nums, int k) {
        int count = 0, sum = 0;
        unordered_map<int,int> pre_sum;
        pre_sum[0]++;
        for (int x : nums) {
            sum += x;
            if (pre_sum.find(sum - k) != pre_sum.end()) count += pre_sum[sum - k];
            pre_sum[sum]++;
      }
        return count;
    }

 

3. Leetcode 523 - Continuous Subarray Sum where sum is a multiple of k


Description:

Given a list of non-negative numbers and a target integer k, write a function to check if the array has a continuous subarray of size at least 2 that sums up to a multiple of k, that is, sums up to n*k where n is also an integer.

Explanation:

bool checkSubarraySum(vector<int>& nums, int k) {

    int n = nums.size(), sum = 0, prev = 0;
    unordered_set<int> mod_set;
    for (int x : nums) {
        sum += x;
        int mod = k == 0 ? sum : sum % k;
        if (mod_set.find(mod) != mod_set.end()) return true;
        mod_set.insert(prev);
        prev = mod;
    }
    return false;
    
}

 

4. Leetcode 525 - Longest Contiguous Binary Array


Description:

Given a binary array, find the maximum length of a contiguous subarray with equal number of 0 and 1.

Explanation:

int findMaxLength(vector<int>& nums) {
    int max_sum = 0, pre_sum = 0;
    int size = nums.size();
    vector<int> arr(size*2 + 1, -1);
    
    for (int i = 0; i < nums.size(); i++) {
        nums[i] ? pre_sum++ : pre_sum--;
        if (pre_sum == 0) max_sum = i + 1;
        else if (arr[pre_sum + size] == -1) arr[pre_sum + size] = i;
        else (max_sum = max(max_sum, i - arr[pre_sum + size]));
    }
    
    return max_sum;
}

 

5. Leetcode 53 - Maximum Subarray - Kadane’s algorithm


Description:

Given an integer array nums, find the contiguous subarray (containing at least one number) which has the largest sum and return its sum.

Input: [-2,1,-3,4,-1,2,1,-5,4]

Output: 6

Explanation: [4,-1,2,1] has the largest sum = 6

Solution: Using Kadane’s algorithm. Make sum = nums[i] when sum till before i, drops below 0.

class Solution {
public:
    int maxSubArray(vector<int>& nums) {
        if (nums.empty()) return 0;
        int maxsum = nums[0];
        int sum = nums[0];
        for (int i = 1; i < nums.size(); i++) {
            if (sum < 0) sum = 0;
            sum += nums[i];
            if (maxsum < sum) maxsum = sum;
        }
        return maxsum;
    }
};

 

6. Leetcode 918 - Maximum Sum Circular Subarray


Description:

Given a circular array C of integers represented by A, find the maximum possible sum of a non-empty subarray of C.

Input: [1,-2,3,-2]

Output: 3

Explanation: Subarray [3] has maximum sum 3

Solution: Using both max subarray and min subarray

int maxSubarraySumCircular(vector<int>& A) {
    int total = 0, maxSum = A[0], curMax = 0, minSum = A[0], curMin = 0;
    for (int& a : A) {
        curMax = max(curMax + a, a);
        maxSum = max(maxSum, curMax);
        curMin = min(curMin + a, a);
        minSum = min(minSum, curMin);
        total += a;
    }
    return maxSum > 0 ? max(maxSum, total - minSum) : maxSum;
}