Given an array of integers heights
representing the histogram's bar height where the width of each bar is 1
, return the area of the largest rectangle in the histogram.
Example 1:
Input: heights = [2,1,5,6,2,3] Output: 10 Explanation: The above is a histogram where width of each bar is 1. The largest rectangle is shown in the red area, which has an area = 10 units.
Example 2:
Input: heights = [2,4] Output: 4
Constraints:
1 <= heights.length <= 105
0 <= heights[i] <= 104
When you get asked this question in a real-life environment, it will often be ambiguous (especially at FAANG). Make sure to ask these questions in that case:
The brute force strategy for the histogram problem is all about trying everything. We will look at every possible rectangle we can form within the histogram and calculate its area. Finally, we find the rectangle with the biggest area.
Here's how the algorithm would work step-by-step:
def largest_rectangle_in_histogram_brute_force(heights):
largest_area = 0
number_of_heights = len(heights)
for left_edge in range(number_of_heights):
# Consider each bar as the potential left edge
for right_edge in range(left_edge, number_of_heights):
minimum_height = float('inf')
for index in range(left_edge, right_edge + 1):
minimum_height = min(minimum_height, heights[index])
# Find the smallest height between left and right edges
width = right_edge - left_edge + 1
current_area = minimum_height * width
# Expand the rectangle to the right and calculate area
largest_area = max(largest_area, current_area)
# Update largest area if necessary
return largest_area
The most efficient way to solve this is to keep track of the potential for building tall rectangles as you go. We use a special tool to help us remember where we are in the histogram and efficiently find the best rectangle.
Here's how the algorithm would work step-by-step:
def largestRectangleArea(heights):
stack = []
max_area = 0
index = 0
while index < len(heights):
if not stack or heights[index] > heights[stack[-1]]:
stack.append(index)
index += 1
else:
# Current height is less so calculate area.
top_of_stack = stack.pop()
area = (heights[top_of_stack] *
((index - stack[-1] - 1) if stack else index))
max_area = max(max_area, area)
# Calculate the area for the remaining bars.
while stack:
top_of_stack = stack.pop()
area = (heights[top_of_stack] *
((index - stack[-1] - 1) if stack else index))
# Store the largest area.
max_area = max(max_area, area)
return max_area
Case | How to Handle |
---|---|
Null or empty input array | Return 0 as there are no bars to form a rectangle. |
Array with a single element | Return the value of the single element as the largest area is the height itself. |
Array with all identical values | The largest rectangle area is the height multiplied by the width (array length). |
Array with heights in strictly increasing order | The algorithm should correctly calculate decreasing areas from right to left. |
Array with heights in strictly decreasing order | The algorithm should correctly calculate increasing areas from left to right. |
Large input array (performance consideration) | The stack-based approach handles large arrays efficiently with O(n) time complexity. |
Heights with very large values that can lead to integer overflow when calculating area | Use long data type for calculating area to prevent overflow. |
Array containing zero values | Zero values should be treated as valid heights, potentially limiting the area of rectangles. |