The Peak of a Mountain Array

Prereq: Vanilla Binary Search and Finding the Boundary with Binary Search

A mountain array is defined as an array that

  • has at least 3 elements
  • has an element with the largest value called "peak", with index k. The array elements monotonically increase from the first element to A[k], and then monotonically decreases from A[k + 1] to the last element of the array. Thus creating a "mountain" of numbers.

That is, given A[0]<...<A[k-1]<A[k]>A[k+1]>...>A[n-1], we need to find the index k. Note that the peak element is neither the first nor the last element of the array.

Find the index of the peak element. Assume there is only one peak element.

Input: 0 1 2 3 2 1 0

Output: 3

Explanation: the largest element is 3 and its index is 3.

Try it yourself

Explanation

The peak element is always larger than the next element. Applying the filter of arr[i] > arr[i + 1] we get a boolean array. A minor edge case is for the last element as it has no next element. In that case, we assume its next element is negative infinity.

Now the problem is reduced to finding the first true element in a boolean array. And we already know how to do this from Find the Boundary module.

Time Complexity: O(log(n))

1from typing import List
2
3def peak_of_mountain_array(arr: List[int]) -> int:
4    left, right = 0, len(arr) - 1
5    boundary_index = -1
6
7    while left <= right:
8        mid = (left + right) // 2
9        if arr[mid] > arr[mid + 1]:
10            boundary_index = mid
11            right = mid - 1
12        else:
13            left = mid + 1
14
15    return boundary_index
16
17if __name__ == '__main__':
18    arr = [int(x) for x in input().split()]
19    res = peak_of_mountain_array(arr)
20    print(res)
21