接雨水-单调栈解法

发布时间 2023-08-30 20:24:15作者: _春华秋实

题目链接

给定 n 个非负整数表示每个宽度为 1 的柱子的高度图,计算按此排列的柱子,下雨之后能接多少雨水。

示例 1:

请在此添加图片描述

输入:height = [0,1,0,2,1,0,1,3,2,1,2,1]
输出:6
解释:上面是由数组 [0,1,0,2,1,0,1,3,2,1,2,1] 表示的高度图,在这种情况下,可以接 6 个单位的雨水(蓝色部分表示雨水)。 

解题思路

单调栈:栈内元素单调按照递增(递减)顺序排列的栈

链接

func trap(height []int) (ans int) {
    stack := []int{} //使用切片模拟单调栈
    for i, h := range height {
        //循环遍历单调栈中的下标,求每个下标对应的面积
        for len(stack) > 0 && h > height[stack[len(stack)-1]] {
            //栈顶元素下标
            top := stack[len(stack)-1]
            stack = stack[:len(stack)-1]
            if len(stack) == 0 {
                break
            }
            //栈顶的下一个元素下标
            left := stack[len(stack)-1]
            //求到这个下标的低洼处的宽度和高度
            curWidth := i - left - 1 
            curHeight := min(height[left], h) - height[top]
            ans += curWidth * curHeight
            // fmt.Printf("%d -- %d -- %d -- %d \n", left, curWidth, curHeight, ans)
        }
        stack = append(stack, i)
    }
    return
}

func min(a, b int) int {
    if a < b {
        return a
    }
    return b
}