题意
给定一个有 \(n\) 个正整数的数组,一次操作中,可以把任意一个元素加一或减一。(元素可被减至负数或 \(0\)),求使得原序列严格递增的求最小操作次数。
题解
首先有一个常规的想法,将 \(a_i\) 减去 \(i\),这样可使问题转化为将序列变为 非严格递增序列。
然后有一个非常诡异的做法。
用优先队列维护修改过的序列的最大值,每次新加入一个数 \(x\),的时候,我们先将其加入优先队列,然后取出堆顶 \(y\)(取出最靠后的最大值),如果 \(x\geq y\) 无所谓,如果 \(x<y\),则将 \(y\) 修改为 \(x\)。
至于证明(感性理解一下)
我们考虑任意一种调整方法,发现对于逆序对 \(x,y\) \((x<y,a_x>a_y)\),不难发现 \(y\) 不可能减小(否则不优),而这里的做法钦定了 \(y\) 不减小,所以更优。
然后考虑一个问题:若 \(y\) 变为 \(x\) , \(y\) 前面的最大值 \(z\) 大于 \(y\) 了,这样是否合法。
这时候只需要关注 \(z\) 的最终值 \(z'\) 即可。
不难发现,如果 \(z'\geq x\) 就将 \(x\) 抬到 \(y\), \(y\) 减到 \(z\) 则效果相同花费不变。
\(z'\leq x\) 则调整方式没任何问题。