这是我做过最难的一题了,真的是推的天昏地暗。
题目大意
现在给你
n
n
n 个盒子,每个盒子里放着
a
i
a_i
ai 个物品,总货物数量
S
=
∑
i
=
1
n
a
i
S=\sum_{i=1}^n a_i
S=∑i=1nai。
你想通过一系列操作让每个盒子里变成
b
i
b_i
bi 个物品,满足
∑
i
=
1
n
b
i
=
S
\sum_{i=1}^n b_i = S
∑i=1nbi=S。
每次操作可以把一个盒子中的一个物品移动到它相邻的盒子中,对
i
,
i
+
1
i,i+1
i,i+1 号两个盒子做一次操作的代价是
w
i
w_i
wi。
显然盒子中的物品数量在任意时刻都不能为负数。
你需要对每一种 b b b 求出操作代价最小值的和。若设 v a l ( b 1 , b 2 , … , b n ) val(b_1,b_2,\dots,b_n) val(b1,b2,…,bn) 为让第 i i i 个盒子刚好有 b i b_i bi 个物品的最小代价,那么你需要求出所有满足 ∑ i = 1 n b i = S \sum_{i=1}^n b_i = S ∑i=1nbi=S 的非负整数数组 b b b 的 ∑ b v a l ( b 1 , b 2 , … , b n ) \sum \limits _{b} val(b_1,b_2,\dots,b_n) b∑val(b1,b2,…,bn)。
题解
假设已知 a , b a,b a,b。考虑现在已经让前 i − 1 i-1 i−1 个盒子满足条件,然后需要在 i i i 和 i + 1 i+1 i+1 之前移动,则显然: a n s = ∑ i = 1 n − 1 w i ∣ ∑ j = 1 i a j − ∑ j = 1 i b j ∣ ans=\sum\limits_{i=1} ^{n-1} w_i \Bigg| \sum\limits_{j=1}^i a_j - \sum\limits_{j=1}^i b_j \Bigg| ans=i=1∑n−1wi j=1∑iaj−j=1∑ibj
考虑先消掉一层循环,观察到
∑
j
=
1
i
a
/
b
j
\sum\limits_{j=1}^i a / b_j
j=1∑ia/bj 都是一个数组的前缀和形式,所以设
c
,
d
c,d
c,d 分别为
a
,
b
a,b
a,b 的前缀和,在已知
a
,
b
a,b
a,b 的情况下答案可以转化为:
a
n
s
=
∑
i
=
1
n
−
1
w
i
∣
c
i
−
d
i
∣
ans=\sum\limits_{i=1} ^{n-1} w_i | c_i - d_i |
ans=i=1∑n−1wi∣ci−di∣
由于
b
b
b 未知,因此
d
d
d 也是未知的,那么答案就是
∑
d
∑
i
=
1
n
−
1
w
i
∣
c
i
−
d
i
∣
\sum\limits_{d} \sum\limits_{i=1}^{n-1} w_i | c_i - d_i |
d∑i=1∑n−1wi∣ci−di∣
观察第二层循环,我们枚举了
i
i
i,而由于
a
i
a_i
ai 已知,所以
c
i
c_i
ci 也是已知。所以考虑枚举
d
i
d_i
di 的方案数,这里令
c
n
t
(
i
,
d
i
)
cnt(i, d_i)
cnt(i,di) 为方案数,则把外层循环扔到里面,答案可以表示为
∑
i
=
1
n
−
1
w
i
∑
d
i
=
0
S
∣
c
i
−
d
i
∣
×
c
n
t
(
i
,
d
i
)
\sum\limits_{i=1}^{n-1} w_i \sum\limits_{d_i=0}^S | c_i - d_i | \times cnt(i, d_i)
i=1∑n−1widi=0∑S∣ci−di∣×cnt(i,di)。
考虑从
d
d
d 数列的性质进行分析,会发现由于
b
b
b 是非负整数组,
0
≤
d
1
≤
d
2
≤
⋯
≤
d
i
⋯
≤
d
n
=
S
0 \leq d_1 \leq d_2 \leq \dots \leq d_i \dots \leq d_n = S
0≤d1≤d2≤⋯≤di⋯≤dn=S。
由于我们枚举
d
i
d_i
di,并且
d
n
=
S
d_n=S
dn=S 是已知,所以数列可以分为
[
1
,
i
)
[1,i)
[1,i) 和
(
i
,
n
)
(i,n)
(i,n)。
接下来考虑求出
0
≤
d
1
≤
d
2
≤
⋯
≤
d
i
0 \leq d_1 \leq d_2 \leq \dots \leq d_i
0≤d1≤d2≤⋯≤di 解的数量。
于是你会发现这个
≤
\leq
≤ 让你非常难受。怎么办呢?转化一下 【组合数学】8 种盒中放球问题详解,这相当于是第四条,把若干个相同的物品放入几个不同的盒子,盒子允许为空的问题。
这一步转化很重要,我们以
i
i
i 为分界点,左边
[
1
,
i
)
[1,i)
[1,i) 有
(
i
−
1
)
(i-1)
(i−1) 个数的方案数就是
(
d
i
+
i
−
1
i
−
1
)
\binom{d_i + i - 1}{i - 1}
(i−1di+i−1),右边
(
i
,
n
)
(i,n)
(i,n) 有
n
−
i
−
1
n - i - 1
n−i−1 个数的方案数就是
(
S
+
n
−
d
i
−
i
−
1
n
−
i
−
1
)
\binom{S + n - d_i - i - 1}{n - i - 1}
(n−i−1S+n−di−i−1)。
有了这两个式子,再代入 c n t ( i , d i ) cnt(i,d_i) cnt(i,di) 就可以得出答案:
a n s = ∑ i = 1 n − 1 w i ( ∑ d i = 0 S ∣ c i − d i ∣ × ( d i + i − 1 i − 1 ) × ( S + n − d i − i − 1 n − i − 1 ) ) ans=\sum\limits_{i=1}^{n-1} w_i \Bigg( \sum\limits_{d_i=0}^S | c_i - d_i | \times \binom{d_i + i - 1}{i - 1} \times \binom{S + n - d_i - i - 1}{n - i - 1} \Bigg) ans=i=1∑n−1wi(di=0∑S∣ci−di∣×(i−1di+i−1)×(n−i−1S+n−di−i−1))
由于 ∣ x − y ∣ = 2 × ( x − y ) + ( y − x ) |x-y| = 2 \times (x-y) + (y-x) ∣x−y∣=2×(x−y)+(y−x)(至于证明,自己手推一下 x − y x-y x−y 的正负性),所以:
a n s = ∑ i = 1 n − 1 w i ( 2 × ∑ d i = 0 c i ( c i − d i ) × ( d i + i − 1 i − 1 ) × ( S + n − d i − i − 1 n − i − 1 ) + ∑ d i = 0 S ( d i − c i ) × ( d i + i − 1 i − 1 ) × ( S + n − d i − i − 1 n − i − 1 ) ) ans=\sum\limits_{i=1}^{n-1} w_i \Bigg( 2 \times \sum\limits_{d_i=0}^{c_i} (c_i - d_i) \times \binom{d_i + i - 1}{i - 1} \times \binom{S + n - d_i - i - 1}{n - i - 1} + \sum\limits_{d_i=0}^S (d_i - c_i) \times \binom{d_i + i - 1}{i - 1} \times \binom{S + n - d_i - i - 1}{n - i - 1}\Bigg) ans=i=1∑n−1wi(2×di=0∑ci(ci−di)×(i−1di+i−1)×(n−i−1S+n−di−i−1)+di=0∑S(di−ci)×(i−1di+i−1)×(n−i−1S+n−di−i−1))
这个式子过于复杂,我们设:
f
(
n
,
S
,
i
,
k
)
=
∑
d
i
=
0
k
(
d
i
+
i
−
1
i
−
1
)
×
(
S
+
n
−
d
i
−
i
−
1
n
−
i
−
1
)
f(n,S,i,k)=\sum\limits_{d_{i}=0}^k \binom{d_i + i - 1}{i - 1} \times \binom{S + n - d_i - i - 1}{n - i - 1}
f(n,S,i,k)=di=0∑k(i−1di+i−1)×(n−i−1S+n−di−i−1)
g
(
n
,
S
,
i
,
k
)
=
∑
d
i
=
0
k
d
i
×
(
d
i
+
i
−
1
i
−
1
)
×
(
S
+
n
−
d
i
−
i
−
1
n
−
i
−
1
)
g(n,S,i,k)=\sum\limits_{d_{i}=0}^k d_i \times \binom{d_i + i - 1}{i - 1} \times \binom{S + n - d_i - i - 1}{n - i - 1}
g(n,S,i,k)=di=0∑kdi×(i−1di+i−1)×(n−i−1S+n−di−i−1)
代回答案,则化简为:
a n s = ∑ i = 1 n − 1 w i ( 2 × c i × f ( n , S , i , c i ) − 2 × g ( n , S , i , c i ) + g ( n , S , i , S ) − c i × f ( n , S , i , S ) ) ans=\sum\limits_{i=1}^{n-1} w_i \Bigg( 2 \times c_i \times f(n,S,i,c_i) - 2 \times g(n,S,i,c_i) + g(n,S,i,S) - c_i \times f(n,S,i,S) \Bigg) ans=i=1∑n−1wi(2×ci×f(n,S,i,ci)−2×g(n,S,i,ci)+g(n,S,i,S)−ci×f(n,S,i,S))
但是这仍然不是很好求,所以我们考虑求出 f , g f,g f,g 两个函数的关系。
g
(
n
,
S
,
i
,
k
)
=
∑
d
i
=
0
k
d
i
×
(
d
i
+
i
−
1
i
−
1
)
×
(
S
+
n
−
d
i
−
i
−
1
n
−
i
−
1
)
g(n,S,i,k)=\sum\limits_{d_{i}=0}^k d_i \times \binom{d_i + i - 1}{i - 1} \times \binom{S + n - d_i - i - 1}{n - i - 1}
g(n,S,i,k)=di=0∑kdi×(i−1di+i−1)×(n−i−1S+n−di−i−1)
由于
d
0
=
0
d_0 = 0
d0=0 所以忽略这一位的贡献;另外有
C
n
m
=
C
n
n
−
m
C_n^m = C_n^{n-m}
Cnm=Cnn−m,由此转化式子:
=
∑
d
i
=
1
k
d
i
×
(
d
i
+
i
−
1
d
i
)
×
(
S
+
n
−
d
i
−
i
−
1
n
−
i
−
1
)
=\sum\limits_{d_{i}=1}^k d_i \times \binom{d_i + i - 1}{d_i} \times \binom{S + n - d_i - i - 1}{n - i - 1}
=di=1∑kdi×(didi+i−1)×(n−i−1S+n−di−i−1)
把
d
i
d_i
di 和第一个组合数拆成阶乘的式子:
d
i
×
(
d
i
+
i
−
1
)
!
d
i
!
(
i
−
1
)
!
d_i \times \frac{(d_i + i - 1)!}{d_i ! (i - 1) !}
di×di!(i−1)!(di+i−1)!。
上下同时乘
i
i
i:
d
i
×
(
d
i
+
i
−
1
)
!
×
i
d
i
!
i
!
d_i \times \frac{(d_i + i - 1)! \times i}{d_i ! i !}
di×di!i!(di+i−1)!×i。
化简:
i
×
(
d
i
+
i
−
1
)
!
(
d
i
−
1
)
!
(
i
−
1
)
!
=
i
×
(
d
i
+
i
−
1
i
)
i \times \frac{(d_i + i - 1)!}{(d_i-1)! (i-1)!} = i \times \binom{d_i + i - 1}{i}
i×(di−1)!(i−1)!(di+i−1)!=i×(idi+i−1)。
代入原式:
g ( n , S , i , k ) = ∑ d i = 1 k i × ( d i + i − 1 i ) × ( S + n − d i − i − 1 n − i − 1 ) g(n,S,i,k)=\sum\limits_{d_{i}=1}^k i \times \binom{d_i + i - 1}{i} \times \binom{S + n - d_i - i - 1}{n - i - 1} g(n,S,i,k)=di=1∑ki×(idi+i−1)×(n−i−1S+n−di−i−1)
我们当然是要求
g
,
f
g,f
g,f 两个函数的关系,所以要把
g
g
g 转化为
f
f
f 的形式。
观察到
(
d
i
+
i
−
1
i
)
\binom{d_i + i - 1}{i}
(idi+i−1) 中下面的 “
i
i
i” 并不与上面 “
i
−
1
i - 1
i−1” 相等,所以考虑把所有的
d
i
d_i
di 都
−
1
-1
−1。
同时把公因式
i
i
i 提出来。
于是可得:
g ( n , S , i , k ) = i × ∑ d i = 0 k − 1 ( d i + i i ) × ( S + n − d i − i − 2 n − i − 1 ) g(n,S,i,k)=i \times \sum\limits_{d_{i}=0}^{k-1} \binom{d_i + i}{i} \times \binom{S + n - d_i - i - 2}{n - i - 1} g(n,S,i,k)=i×di=0∑k−1(idi+i)×(n−i−1S+n−di−i−2)
可以转化为 f f f 的形式:
g ( n , S , i , k ) = i × f ( n + 1 , S − 1 , i + 1 , k − 1 ) g(n,S,i,k)=i \times f(n + 1, S - 1, i + 1, k - 1) g(n,S,i,k)=i×f(n+1,S−1,i+1,k−1)
这样我们就只要维护 f f f 函数就行了。先把答案抄过来:
a
n
s
=
∑
i
=
1
n
−
1
w
i
(
2
×
c
i
×
f
(
n
,
S
,
i
,
c
i
)
−
2
×
g
(
n
,
S
,
i
,
c
i
)
+
g
(
n
,
S
,
i
,
S
)
−
c
i
×
f
(
n
,
S
,
i
,
S
)
)
ans=\sum\limits_{i=1}^{n-1} w_i \Bigg( 2 \times c_i \times f(n,S,i,c_i) - 2 \times g(n,S,i,c_i) + g(n,S,i,S) - c_i \times f(n,S,i,S) \Bigg)
ans=i=1∑n−1wi(2×ci×f(n,S,i,ci)−2×g(n,S,i,ci)+g(n,S,i,S)−ci×f(n,S,i,S))
=
∑
i
=
1
n
−
1
w
i
(
2
×
c
i
×
f
(
n
,
S
,
i
,
c
i
)
−
2
×
i
×
f
(
n
+
1
,
S
−
1
,
i
+
1
,
c
i
−
1
)
+
i
×
f
(
n
+
1
,
S
−
1
,
i
+
1
,
S
−
1
)
−
c
i
×
f
(
n
,
S
,
i
,
S
)
)
=\sum\limits_{i=1}^{n-1} w_i \Bigg( 2 \times c_i \times f(n,S,i,c_i) - 2 \times i \times f(n+1,S-1,i+1,c_i-1) + i \times f(n+1,S-1,i+1,S-1) - c_i \times f(n,S,i,S) \Bigg)
=i=1∑n−1wi(2×ci×f(n,S,i,ci)−2×i×f(n+1,S−1,i+1,ci−1)+i×f(n+1,S−1,i+1,S−1)−ci×f(n,S,i,S))
=
∑
i
=
1
n
−
1
w
i
(
c
i
×
(
2
×
f
(
n
,
S
,
i
,
c
i
)
−
f
(
n
,
S
,
i
,
S
)
)
+
i
×
(
f
(
n
+
1
,
S
−
1
,
i
+
1
,
S
−
1
)
−
2
×
f
(
n
+
1
,
S
−
1
,
i
+
1
,
c
i
−
1
)
)
)
=\sum\limits_{i=1}^{n-1} w_i \Bigg( c_i \times \Big( 2 \times f(n,S,i,c_i) - f(n,S,i,S) \Big) + i \times \Big( f(n+1,S-1,i+1,S-1) -2 \times f(n+1,S-1,i+1,c_i-1) \Big) \Bigg)
=i=1∑n−1wi(ci×(2×f(n,S,i,ci)−f(n,S,i,S))+i×(f(n+1,S−1,i+1,S−1)−2×f(n+1,S−1,i+1,ci−1)))
这个式子看起来就非常的不可做,但是可以发现当中的
i
i
i 和
c
i
c_i
ci 都是单调不降的。
所以考虑增量维护这些
f
f
f。
显然四个参数中,前两个是定值,所以只需要考虑后两个的变化。现在想如何通过 f ( n , S , i , k ) f(n,S,i,k) f(n,S,i,k) 推导出 f ( n , S , i , k + 1 ) f(n,S,i,k+1) f(n,S,i,k+1) 和 f ( n , S , i + 1 , k ) f(n,S,i+1,k) f(n,S,i+1,k)。
非常显然地,根据定义可以求出 f ( n , S , i , k + 1 ) = f ( n , S , i , k ) + ( ( k + 1 ) + i − 1 i − 1 ) × ( S − ( k + 1 ) + n − i − 1 n − i − 1 ) f(n,S,i,k+1)=f(n,S,i,k) + \binom{(k+1)+i-1}{i-1} \times \binom{S-(k+1)+n-i-1}{n-i-1} f(n,S,i,k+1)=f(n,S,i,k)+(i−1(k+1)+i−1)×(n−i−1S−(k+1)+n−i−1)。即:
f ( n , S , i , k + 1 ) = f ( n , S , i , k ) + ( k + i i − 1 ) × ( S − k + n − i − 2 n − i − 1 ) f(n,S,i,k+1)=f(n,S,i,k) + \binom{k+i}{i-1} \times \binom{S-k+n-i-2}{n-i-1} f(n,S,i,k+1)=f(n,S,i,k)+(i−1k+i)×(n−i−1S−k+n−i−2)
而对于通过
f
(
n
,
S
,
i
,
k
)
f(n,S,i,k)
f(n,S,i,k) 推导
f
(
n
,
S
,
i
+
1
,
k
)
f(n,S,i+1,k)
f(n,S,i+1,k),我们探究它的组合意义。
由于前面定义
f
(
n
,
S
,
i
,
k
)
=
∑
d
i
=
0
k
(
d
i
+
i
−
1
i
−
1
)
×
(
S
+
n
−
d
i
−
i
−
1
n
−
i
−
1
)
f(n,S,i,k)=\sum\limits_{d_{i}=0}^k \binom{d_i + i - 1}{i - 1} \times \binom{S + n - d_i - i - 1}{n - i - 1}
f(n,S,i,k)=di=0∑k(i−1di+i−1)×(n−i−1S+n−di−i−1),会发现
f
(
n
,
S
,
i
,
k
)
f(n,S,i,k)
f(n,S,i,k) 即在坐标轴上只能向右或向上走,从
(
0
,
0
)
→
(
i
−
1
,
d
i
)
→
(
i
,
d
i
)
→
(
n
−
1
,
S
)
(0,0) \rightarrow (i-1,d_i) \rightarrow (i,d_i) \rightarrow (n-1,S)
(0,0)→(i−1,di)→(i,di)→(n−1,S) 的方案数。
画出示意图(奇丑无比):
由于
d
i
∈
[
0
,
k
]
d_i \in [0,k]
di∈[0,k] 所以可以发现当从第
k
k
k 行走向
k
+
1
k+1
k+1 行的时候,点的横坐标(注意!是横坐标)必定大于
i
−
1
i-1
i−1。
于是我们转为枚举这个点,
f
(
n
,
S
,
i
,
k
)
f(n,S,i,k)
f(n,S,i,k) 的组合意义就是
(
0
,
0
)
→
(
j
,
k
)
→
(
j
,
k
+
1
)
→
(
n
−
1
,
S
)
(0,0) \rightarrow (j,k) \rightarrow (j,k+1) \rightarrow (n-1,S)
(0,0)→(j,k)→(j,k+1)→(n−1,S) 的方案数(
j
∈
[
i
,
n
]
j \in [i,n]
j∈[i,n])。
因此可以重新写出它的表达式:
f ( n , S , i , k ) = ∑ j = i n ( j + k j ) × ( n + S − j − k − 2 S − k − 1 ) f(n,S,i,k) = \sum\limits_{j=i}^n \binom{j+k}{j} \times \binom{n+S-j-k-2}{S-k-1} f(n,S,i,k)=j=i∑n(jj+k)×(S−k−1n+S−j−k−2)
于是可以推出它的增量转移式:
f ( n , S , i + 1 , k ) = f ( n , S , i , k ) − ( i + k i ) × ( n + s − i − k − 2 S − k − 1 ) f(n,S,i+1,k) = f(n,S,i,k) - \binom{i+k}{i} \times \binom{n+s-i-k-2}{S-k-1} f(n,S,i+1,k)=f(n,S,i,k)−(ii+k)×(S−k−1n+s−i−k−2)
有了上述两个增量转移式,就可以增量维护四个
f
f
f 函数求答案了。
为了方便再抄一遍:
f ( n , S , i , k + 1 ) = f ( n , S , i , k ) + ( k + i i − 1 ) × ( S − k + n − i − 2 n − i − 1 ) f(n,S,i,k+1)=f(n,S,i,k) + \binom{k+i}{i-1} \times \binom{S-k+n-i-2}{n-i-1} f(n,S,i,k+1)=f(n,S,i,k)+(i−1k+i)×(n−i−1S−k+n−i−2)
f ( n , S , i + 1 , k ) = f ( n , S , i , k ) − ( i + k i ) × ( n + s − i − k − 2 S − k − 1 ) f(n,S,i+1,k) = f(n,S,i,k) - \binom{i+k}{i} \times \binom{n+s-i-k-2}{S-k-1} f(n,S,i+1,k)=f(n,S,i,k)−(ii+k)×(S−k−1n+s−i−k−2)
纯属口胡,代码未补。