
The Prefix Sum technique is one of the simplest—and most powerful—patterns in algorithm design.
Its purpose is straightforward: precompute cumulative information so that later queries become trivial.
At its core, the idea is:
Given an array nums, the prefix sum array prefix is defined as:
This means each prefix element stores the sum from the start up to index i.
Without prefix sums, computing the sum of a range requires scanning the array, so per query.
With prefix sums:
So, O(1) per query after an initial O(n) preprocessing
This transformation is why prefix sums appear a lot in algorithmic problems involving:
Generalizing what we saw earlier, we can write a general definition of prefix sum.
Once you compute the cumulative array prefix, any range sum becomes a simple subtraction:
This works because contains the sum from the start up to ,
while contains the sum up to just before the range begins.
Subtracting the two removes everything outside the interval and leaves only the sum of the subarray .
There is one small edge case: when the range starts at index 0.
In that situation, there's nothing before the range, so the formula simplifies to:
This compact idea, “a range sum is just the difference of two prefix sums”, is the foundation of all prefix-sum techniques.
Below are some common patterns that build upon the basic prefix sum idea.
The most fundamental version of the technique.
It leverages the standard definition of prefix sums and code it.
You precompute an auxiliary array prefix[] where each entry contains
the cumulative sum from the start of the array up to index i.
When the goal is to find subarrays with a specific target sum, the
standard prefix array isn't enough.
We need to know how many times a certain prefix sum has appeared
before.
The idea behind this the following one. If
then the subarray sums to . This means:
So for each j, we only need to check whether has appeared before.
A hash map (prefix → frequency) lets us do this in O(1).
So during a scan of the array:
currentPrefix be the running sum.currentPrefix - k has been seen before.This unlocks problems like Subarray Sum Equals K.
Some problems ask whether a subarray sum is divisible by k.
Key identity:
implies
So instead of storing prefix sums themselves, we store:
in a hash map with their frequencies. Every time we encounter a prefix sum whose modulo k has appeared before, it means that the “excess amount” beyond a multiple of k is the same as in a previous prefix. Because both prefixes leave the same remainder when divided by k, the region between them must add up to an exact multiple of k. Therefore, each previous occurrence of that remainder corresponds to a new subarray whose sum is divisible by k.
Used in problems involving binary arrays or balancing conditions.
Transform the array:
0 → -11 → +1After this transformation, a balanced subarray (equal number of 0s
and 1s) becomes a subarray with sum = 0.
Then the problem becomes "Find the longest subarray whose prefix sums repeat".
Because if:
then the subarray sums to 0.
This technique is central in Contiguous Array.
Below you can find a summary table of time and space complexities for each pattern discussed.
| Operation / Pattern | Time Complexity | Space Complexity |
|---|---|---|
| Build prefix array | O(n) | O(n) |
| Range sum query (L, R) | O(1) | O(n) |
| Prefix sum + hash map (target sum) | O(n) average | O(n) |
| Prefix sum modulo K | O(n) average | O(n) |
| Balance tracking (+1 / -1 transform) | O(n) | O(n) |
| Exercise | Technique | Solution |
|---|---|---|
| Range Sum Query – Immutable | Classic Prefix Sum | Solution |
| Subarray Sum Equals K | Prefix Sum + Hash Map | Solution |
| Subarray Sums Divisible by K | Prefix Sum + Modulo Buckets | Solution |
| Continuous Subarray Sum | Prefix Sum + Modulo Constraints | Solution |
| Contiguous Array | Balance Tracking + Prefix Sum | Solution |