给定长度为 的序列
定义 的最大值, 同理。求:

取模。

分治,对于区间 ,考虑 的区间造成的贡献。

我们记录三个指针:

  • ,表示现在考虑到了 这部分区间。 开始向前枚举,可以在这个过程中记录 的最值 ,显然这两个东西是单调的;

  • ,表示对于当前 $i$,在 时左半部分最大值占主导地位,即 。显然这个东西也是单调的。

  • ,与 类似,不过是最小值。

然后可以把 这部分区间分成三部分:

  • 所有最值都是左边占主导,每个区间贡献都是
  • 所有最值都是右边主导,可预处理 $Max(mid+1,r)\times Min(mid+1,r)$ 的前缀和快速得到;
  • ,一部分左边主导,预处理右边 的前缀和即可。

然后就做完了 qwq。

CODE

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
#include <bits/stdc++.h>
using namespace std;
#define int long long

inline int read() {
int x = 0, f = 0; char c = 0;
while (!isdigit(c)) f |= c == '-', c = getchar();
while (isdigit(c)) x = (x << 3) + (x << 1) + (c & 15), c = getchar();
return f ? -x : x;
}

#define N 100005
#define P 1000000007

int n, a[N], res, mn[N], mx[N], smn[N], smx[N], s[N];

void cdx(int l, int r) {
if (l == r) {
res = (res + a[l] * a[r] % P) % P;
return;
}
int mid = (l + r) >> 1;
cdx(l, mid), cdx(mid + 1, r);
mn[mid] = 1e9, mx[mid] = 0;
s[mid] = smx[mid] = smn[mid] = 0;
for (int i = mid + 1; i <= r; i ++) {
mn[i] = min(mn[i - 1], a[i]);
mx[i] = max(mx[i - 1], a[i]);
s[i] = (s[i - 1] + mn[i] * mx[i] % P) % P;
}
mn[mid] = 0;
for (int i = mid + 1; i <= r; i ++) {
smn[i] = (smn[i - 1] + mn[i]) % P;
smx[i] = (smx[i - 1] + mx[i]) % P;
}
for (int i = mid, j = mid, k = mid, lmx = 0, lmn = 1e9; i >= l; i --) {
lmx = max(lmx, a[i]), lmn = min(lmn, a[i]);
while (j < r && mx[j + 1] <= lmx) j ++;
while (k < r && mn[k + 1] >= lmn) k ++;
(res += (s[r] - s[max(j, k)] + P) % P) %= P;
(res += lmx * lmn % P * max(0ll, min(j, k) - mid) % P) %= P;
if (j <= k) (res += lmn * ((smx[k] - smx[j] + P) % P) % P) %= P;
else (res += lmx * ((smn[j] - smn[k] + P) % P) % P) %= P;
}
for (int i = mid; i <= r; i ++) mn[i] = mx[i] = s[i] = 0;
}

signed main() {
freopen("simple.in", "r", stdin);
freopen("simple.out", "w", stdout);
n = read();
for (int i = 1; i <= n; i ++) {
a[i] = read();
}
cdx(1, n), printf("%lld\n", res);
return 0;
}


本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!