Find Peak Element

Medium Binary Search Unique 1-D Binary Search Original on LeetCode

Find Peak Element is a medium binary search problem solved with the unique 1-d binary search pattern. The best approach, optimal (binary search on the slope), runs in O(log n) time and O(1) space. Below are 2 approaches in Java, from linear scan up.

Problem

A peak is an element strictly greater than its neighbours. Neighbours outside the array count as negative infinity, and no two adjacent values are equal. Return the index of any peak in O(log n) time.

Examples

Example 1

Input
nums = [1, 3, 2, 4, 1]
Output
1 or 3
Why
Either peak is accepted.

Example 2

Input
nums = [5, 4, 3]
Output
0

Constraints

  • 1 <= nums.length <= 1000
  • nums[i] != nums[i + 1]; treat nums[-1] = nums[n] = -infinity.
  • O(log n).

Animated walkthrough

A narrated, step-by-step animation that builds the solution from the idea up. Press play, or step through it at your own pace.

Concepts first, then the problem and every approach, step by step.

Space to play or pause · ← → to jump a step · click or drag the bar to seek

Solutions

Try it yourself first. Then compare: each approach lists its idea, the steps, its time and space, and the Java code.

ApproachTimeSpace
Linear scanO(n)O(1)
Optimal (binary search on the slope)O(log n)O(1)

1Linear scan

TimeO(n)
SpaceO(1)

Return the first i where nums[i] > nums[i + 1]; if none, the last index.

  1. for i in 0..n-2: if nums[i] > nums[i+1] return i.
  2. Return n - 1.
Java
class Solution {
    public int findPeakElement(int[] nums) {
        for (int i = 0; i + 1 < nums.length; i++) if (nums[i] > nums[i + 1]) return i;
        return nums.length - 1;
    }
}

2Optimal (binary search on the slope)

TimeO(log n)
SpaceO(1)

Compare nums[mid] with nums[mid + 1]. If the right side is higher, a peak exists on the right, since the edge counts as -infinity. Otherwise a peak exists at mid or to its left.

  1. lo = 0, hi = n - 1.
  2. If nums[mid] < nums[mid + 1]: lo = mid + 1, else hi = mid.
  3. Return lo.
Java
class Solution {
    public int findPeakElement(int[] nums) {
        int lo = 0, hi = nums.length - 1;
        while (lo < hi) {
            int mid = (lo + hi) >>> 1;
            if (nums[mid] < nums[mid + 1]) lo = mid + 1;
            else hi = mid;
        }
        return lo;
    }
}

Edge cases to test

  • Strictly increasing (peak at the end)
  • Strictly decreasing (peak at 0)
  • Single element

Hints

Hint 1

If nums[mid] < nums[mid + 1], you are on an uphill slope. Walking uphill must reach a peak.

FAQ

What is the best time complexity for Find Peak Element?

Optimal (binary search on the slope) runs in O(log n) time and O(1) extra space.

Which pattern does Find Peak Element use?

It is a binary search problem that uses the unique 1-d binary search pattern. Other problems with the same pattern: First Bad Version, Single Element in a Sorted Array.

Is there a brute force solution for Find Peak Element?

Yes. Linear scan takes O(n) time and O(1) space. Return the first i where nums[i] nums[i + 1]; if none, the last index.

Which edge cases should I test for Find Peak Element?

Strictly increasing (peak at the end); Strictly decreasing (peak at 0); Single element.