对于所有 0≤j<i 且 i<k≤n−1,满足 nums[j]<nums[i]<nums[k]
题目的这个要求,相当于:
nums[i] 要大于 i 左边的所有数,也就是大于前缀 [0,i−1] 中的最大值。
nums[i] 要小于 i 右边的所有数,也就是小于后缀 [i+1,n−1] 中的最小值
这可以通过遍历算出来。
定义 sufMin[i] 表示后缀 [i,n−1] 中的最小值。
那么 sufMin[i] 等于 nums[i] 与后缀 [i+1,n−1] 中的最小值,二者取最小值,即
sufMin[i]=min(nums[i],sufMin[i+1])
注意上式需要从右到左遍历 nums 计算。
对于前缀最大值,也同理。
我们可以在从左到右遍历 nums 的过程中,维护前缀最大值 preMax。注意这只需要一个变量,因为我们可以一边计算 preMax,一边计算答案。
class Solution:def sumOfBeauties(self, nums: List[int]) -> int:n = len(nums)suf_min = [0] * n # 后缀最小值,题目中num>0suf_min[n - 1] = nums[n - 1]# sufMin[i]代表的是从索引i开始到数组末尾的最小值。# 而计算这个值的方法是,当前元素nums[i]和下一个位置的sufMin[i+1]中的较小者。# 这意味着,如果我们从数组的最后一个元素开始向前遍历,就可以逐步构建出每个位置的sufMin值。# 例如,考虑一个简单的数组,比如[3,1,4,2]。按照用户的方法,从右向左计算:# 对于i=3(最后一个元素),sufMin[3] = nums[3] = 2。# i=2时,sufMin[2] = min(4, sufMin[3]) = min(4,2) = 2。# i=1时,sufMin[1] = min(1, sufMin[2]) = min(1,2) = 1。# i=0时,sufMin[0] = min(3, sufMin[1]) = min(3,1) = 1。for i in range(n - 2, 1, -1):suf_min[i] = min(suf_min[i + 1], nums[i])ans = 0# 前缀最大值pre_max = nums[0] for i in range(1, n - 1):x = nums[i]# 此时 pre_max 表示 [0, i-1] 中的最大值if pre_max < x < suf_min[i + 1]:ans += 2elif nums[i - 1] < x < nums[i + 1]:ans += 1# 更新后 pre_max 表示 [0, i] 中的最大值pre_max = max(pre_max, x)return ans作者:灵茶山艾府
链接:https://leetcode.cn/problems/sum-of-beauty-in-the-array/solutions/1006001/qian-zhui-zui-da-zhi-hou-zhui-zui-xiao-z-h9qz/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。