提供另一种做法。
考虑枚举 AiA_iAi 和 jjj。于是我们只需要求:
∑k=1,Ak=AiN∣Ai−Aj∣×∣k−j∣\sum_{k=1, A_k=A_i}^N |A_i-A_j| \times |k-j| k=1,Ak =Ai ∑N ∣Ai −Aj ∣×∣k−j∣
所以我们使用 vector<int> b[505] 记录每一个 AkA_kAk 所对应的 kkk.
不难发现,解决问题的瓶颈在于 ∣k−j∣|k-j|∣k−j∣ 的绝对值,所以我们在 b[A[i]] 中,二分找到第一个 kkk 满足 k≥jk \geq jk≥j.
然后设令贡献为 xxx,bib_ibi 的长度为 SiS_iSi ,推式子可以得到:
1. 对于 k<jk<jk<j,有:
x=(j×k−(∑s=1k−1bs))×∣Ai−Aj∣x=(j \times k - (\sum_{s=1}^{k-1} b_s)) \times |A_i-A_j| x=(j×k−(s=1∑k−1 bs ))×∣Ai −Aj ∣
2. 对于 k≥jk \geq jk≥j,有:
x=((∑s=kSibs)−j×(Si−k))×∣Ai−Aj∣x=((\sum_{s=k}^{S_i} b_s)-j \times (S_i - k)) \times |A_i-A_j| x=((s=k∑Si bs )−j×(Si −k))×∣Ai −Aj ∣
其中,求和部分可以使用前缀和优化。
这样,我们就得到了一个 O(nlognmax(A))O(n \log n \max(A))O(nlognmax(A)) 的比 std 时间长、空间慢、更难写的代码。
Code: