leetcode 907. 子数组的最小值之和()

题目链接

907. 子数组的最小值之和

分析

直接DP就好了,求两个数组: left,right,分别表示

left[i] :比i小的左端点,(注意,为避免相等时重复统计,计左不计右)

code

class Solution {
	
	private static final int MOD = 1000000007;
	private void debug(int [] pri) {
		for(int i=0,n = pri.length; i< n ; i++)System.out.print(pri[i]+" ");
		System.out.println();
	}
	public int sumSubarrayMins(int[] A) {
		int n = A.length;
		int[] left = new int[n];
		int[] right = new int[n];
		left[0] =-1;
		for(int i=1 ; i<n ; ++i){
			if(A[i-1] <= A[i])left[i] = i-1;
			else{
				int now = i-1;
				while (now !=-1 &&A[now] > A[i] ) {//算左不算右,避免重复统计
					now = left[now];
				}
				left[i] = now;
			}
		}
		right[n -1] = n;
		for(int i=n -2 ; i >=0 ; --i){
			if(A[i+1]< A[i])right[i] = i+1;
			else{
				int now = i+1;
				while (now != n && A[now] >= A[i]) {
					now = right[now];
				}
				right[i] = now;
			}
		}
//		debug(left);
//		debug(right);
		long ans = 0;
		for(int i=0 ; i<n ; ++i){
			ans += (long)A[i]*(right[i] - i)*(i - left[i]);
			ans %=MOD;
		}
		return (int)ans;
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值