这道题用暴力解法不难,只是肯定会超时。想要优化成O(n)可以用单调栈,单调栈经常用来解决边界问题 直接上代码。
class Solution {
//方法一:超时
public int largestRectangleArea(int[] heights) {
if(heights.length==1) return heights[0];
int max = heights[0];
for(int i=1;i<heights.length;i++){
int min = Integer.MAX_VALUE;
for(int j=i;j>=0;j--){
if(heights[j]<min) min = heights[j];
max = Math.max(max,min*(i-j+1));
}
}
return max;
}
//方法二:单调栈,从该点开始左右遍历寻找边界(单调栈常用来解决寻找最小值问题)
public int largestRectangleArea(int[] heights) {
if(heights.length==1) return heights[0];
int max = heights[0];
int[] left = new int[heights.length]; //存放左侧第一个小于当前位置高度的位置编号
int[] right = new int[heights.length]; //存放右侧第一个小于当前位置高度的位置编号
Stack<Integer> stack = new Stack<>(); //存放边界
for(int i=0;i<heights.length;i++){ //寻找左侧第一个小于当前位置高度的位置编号
while(!stack.isEmpty() && heights[stack.peek()]>=heights[i]) stack.pop();
left[i] = stack.isEmpty()?-1:stack.peek();
stack.push(i);
}
stack.clear();
for(int i=heights.length-1;i>=0;i--){//寻找右侧第一个小于当前位置高度的位置编号
while(!stack.isEmpty() && heights[stack.peek()]>=heights[i]) stack.pop();
right[i] = stack.isEmpty()?heights.length:stack.peek();
stack.push(i);
}
for(int i=0;i<heights.length;i++){
max = Math.max(max,(right[i]-left[i]-1)*heights[i]);
}
return max;
}
}