Insertion Sort

想象一下,冒泡排序交换的两个数一定是原数组的逆序对(反证容易证明:如果不是逆序对,相遇之后不会交换。两个数只有在相遇的时候才会使得下标相对大小互换,相遇之前一定是左的在左,右的在右。而不是逆序对的话,相遇的时候也不会交换,所以就一直不会交换)。

因为有序数组一定没有逆序对,所以逆序对一定换完了,所以swap次数就是逆序对总数。


我的写法是fi,j,表示k[j,n]a[k]<a[i]k的个数。

交换次数就是f1,2+f2,3+...。(通过此式可以发现,如果a[x]<a[y],x,y,交换二者一定不优)

比如枚举交换的是x,y,x<y,那么x之前和y之后的点的fk,k+1都没有改变,对交换次数贡献不变。

对于xyfy,y+1fy,x+1+[a[x]<a[y]?]fx,x+1fx,y+1

如果通过上面的式子退出来逆序对才要交换,[a[x]<a[y]]=0

现在关键是[x+1,y1]中的数的fk,k+1又是如何变化的呢?

昨晚不知道怎么想的,用了权值树状数组查询一段值域的数的个数,其实完全不用。

a[k]>a[x],则fk,k+1+1
a[k]>a[y],则fk,k+11

也就是说,要知道k[x+1,y1],a[k]>t的数的个数。

数据范围很小,再预处理一个gi,x,表示k[1,i],a[k]>x的数的个数不就行了?

那对答案的贡献不就是gy1,a[x]gx,a[x]gy1,a[y]+gx,a[y]吗?

昨晚把上面的式子合并了,写成了a[y]<a[k]<a[x],要1,其实也可以写成a[k]<a[x],减去a[k]<a[y]的。

然后再套一层前缀和预处理,就出来了。

posted @   Zlc晨鑫  阅读(8)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?
· 【译】Visual Studio 中新的强大生产力特性
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 【设计模式】告别冗长if-else语句:使用策略模式优化代码结构
点击右上角即可分享
微信分享提示