G.

定义一次操作:随机选择 $i \in [1, n]$,对所有 $j \in [i, n]$,使得 $a_j = a_j + v$。

$n \leq 5000, m, v \leq 10^9$,m 为操作次数。

求 $\prod a_i$ 的期望值。


$\prod (ai+v+…)$ 每个括号里面选一个产生贡献,只有三种情况。

  • 选择 $a_i$
  • 选择以前用过的 $v$,贡献系数为 $j \times v$,$j$ 为之前操作过的次数。
  • 选择以前没有用过的 $v$,贡献系数为 $(m-j) \times i \times v$,$m - j$ 表示在没有选过的里面选一个,$i$ 表示可以操作在 $[1, i]$。

所以定义 $f_{i, j}$ 为目前长度为 $i$,使用了 $j$ 次操作的期望乘法值。

最后答案为 $\frac{\sum f_{i,j} \times n^{m-j}}{n^m}$。

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
const int P = 1e9 + 7;
int power(int x, int y) {
int res = 1;
while (y) {
if (y % 2 == 1) {
res = 1ll * res * x % P;
}
x = 1ll * x * x % P;
y /= 2;
}
return res;
}
int inv(int x) { return power(x, P - 2); }
void md(int &x) {
if (x >= P)
x -= P;
}
void solve() {
int n, m, v;
cin >> n >> m >> v;
vi a(n);
rep(i, n) cin >> a[i];
vc<vi> f(n + 1, vi(n + 2));
f[0][0] = 1;
rep(i, n) {
rep(j, min(n, m) + 1) {
md(f[i + 1][j] += 1ll * (a[i] + (1ll * j * v) % P) * f[i][j] % P);
md(f[i + 1][j + 1] += 1ll * (m - j) * (i + 1) % P * v % P * f[i][j] % P);
}
}
int ans = 0;
rep(i, min(n, m) + 1) md(ans += 1ll * f[n][i] * power(n, m - i) % P);
cout << 1ll * ans * inv(power(n, m)) % P << "\n";
}