AlgoMaster Logo

First Missing Positive

hardFrequency7 min readUpdated June 23, 2026

Understanding the Problem

We need to find the smallest positive integer (1, 2, 3, ...) that doesn't appear in the array. Negative numbers, zeros, and duplicates do not affect the answer.

If the array has n elements, the answer must lie in the range [1, n+1]. With only n slots, the array can hold at most n distinct positive integers. If those happen to be exactly {1, 2, ..., n}, the answer is n+1. Otherwise at least one number in [1, n] is missing, and the smallest such number is the answer. The answer can never exceed n+1.

So we only care about values between 1 and n. Negatives, zeros, and numbers larger than n cannot be the answer, and they free up the values we do care about to be tracked inside the array itself. That range bound is what makes the O(1) space solution possible.

Key Constraints:

  • 1 <= nums.length <= 10^5 → With up to 100,000 elements, an O(n^2) scan would mean 10^10 operations, too slow. We need O(n log n) or better.
  • -2^31 <= nums[i] <= 2^31 - 1 → Values can be negative, zero, or as large as INT_MAX. Any approach that indexes by value must first check that the value falls in [1, n], otherwise it would index out of bounds or overflow.
  • The problem requires O(n) time and O(1) auxiliary space → This rules out the hash set (O(n) space) and sorting (O(n log n) time). The optimal solution rearranges the input array in place.

Approach 1: Hash Set

Intuition

Put every number into a hash set, then check 1, 2, 3, ... in order until one is not in the set. The hash set gives O(1) membership lookups, so each check is constant time.

This uses O(n) extra space, so it does not meet the O(1) requirement. It is a clean baseline that makes the range bound concrete before we optimize the space away.

Algorithm

  1. Add all elements from nums into a hash set.
  2. Starting from 1, check if each positive integer exists in the set.
  3. Return the first positive integer not found in the set.

Example Walkthrough

1Initialize: add all elements to hash set. Set = {3, 4, -1, 1}
0
3
1
4
2
-1
3
1
1/3

Code

The hash set costs O(n) extra space. The next approach removes that extra space by sorting the array in place and scanning for the first gap in the positive sequence.

Approach 2: Sorting

Intuition

After sorting, the positive integers appear in ascending order. Walk through the sorted array tracking the next positive integer we expect to see, starting at 1. The first expected value that does not appear is the answer.

Sorting trades time (O(n log n)) for space (O(1) with an in-place sort), the opposite trade-off from the hash set. Neither is optimal, but the sorted order makes the gap easy to spot.

Algorithm

  1. Sort the array in ascending order.
  2. Initialize expected = 1 (the first positive integer we're looking for).
  3. Iterate through the sorted array:
    • Skip negative numbers, zeros, and duplicates.
    • If the current number equals expected, increment expected.
    • If the current number is greater than expected, we found the gap.
  4. Return expected.

Example Walkthrough

1Sort the array: [-1, 1, 3, 4]. Initialize expected = 1
0
-1
1
1
2
3
3
4
1/4

Code

Sorting reaches O(1) space but costs O(n log n) time. We do not need the array fully sorted, only each value placed at its own index. The next approach does exactly that in linear time, placing each value v in [1, n] directly at index v-1.

Approach 3: Cyclic Sort (Optimal)

Intuition

The input array can serve as its own hash map. Since the answer is in [1, n+1], we only need to know which values from 1 to n are present, and the array has exactly n slots to record that.

Place each value v in [1, n] at index v-1: value 1 goes to index 0, value 2 to index 1, and so on. After this rearrangement, the answer is a single scan away: the first index i where nums[i] != i + 1 means i + 1 is missing.

The rearrangement is done with cyclic sort. For each index, repeatedly swap the current element toward its correct index, stopping when the element is out of range (negative, zero, or greater than n), already in its correct index, or its target index already holds the same value (a duplicate).

Algorithm

  1. For each index i from 0 to n-1:
    • While nums[i] is in range [1, n] and nums[i] is not in its correct position:
      • Swap nums[i] with nums[nums[i] - 1] (put it where it belongs).
  2. Scan the array: return the first i + 1 where nums[i] != i + 1.
  3. If all positions are correct, return n + 1.

Example Walkthrough

1Initialize: i=0, nums = [3, 4, -1, 1]
0
3
i
1
4
2
-1
3
1
1/8

Code