您的位置:首页 > 其它

整体二分&cdq分治的小总结

2017-03-28 11:57 253 查看
这是一个刚学会(可能是假的)上面两种东西的蒟蒻写的小总结。

大神求不喷 希望能帮到像我一样的蒟蒻

我没怎么看论文 如果想看的话 百度一下别人应该有推荐的。

(如果下面有找不到的题目 可以找我要一下。。)

2017.04.10 upd:注意 有个挺有用的常数优化 在cdq分治 和 整体二分中 如果需要排序 其实是可以使用归并排序来节省时间 不需要sort 当然 具体看题目。

整体二分

整体二分是个很神的东西,它可以把许多复杂的数据结构题化简。它的精髓在于巧妙地利用了离线的特点,把所有的修改、询问操作整体把握。

最经典的就是求带修改的 第K大/小的数

这个做例子挺好的

主要思想就是通过对值的二分 对操作进行分组(询问和修改一起二分)

因为操作是按照时间顺序的 分组之后也是这样 不影响正确性(不懂的可以模拟一下)

我们用树状数组来把<=二分值的修改操作都做一次 对于区间内的询问 我们就问一下当前二分值下有多少个数在前面 如果大于等于询问的k 那肯定在左边里面 否则就减去这个数 然后进去右边找 看看代码就懂了

http://blog.csdn.net/cgh_andy/article/details/66971734

做法相似:

http://blog.csdn.net/cgh_andy/article/details/66971638

也是差不多。。不过是区间修改:

http://blog.csdn.net/cgh_andy/article/details/66971692

cdq分治

在我们平常使用的分治中,每一个子问题只解决它本身(可以说是封闭的)。而在cdq分治中,对于划分出来的两个子问题,前一个子问题用来解决后一个子问题而不是它本身。

在很多问题中(比如大多数数据结构题),我们经常需要处理一些动态问题。然而我们对动态问题的处理总是不如静态问题来的那么方便,于是就有了cdq分治。使用这算法的前提是问题必须具有以下两个性质:

1.修改操作对询问的贡献独立,修改操作互不影响效果。

2.题目允许使用离线算法。

大致过程:(下把询问与修改统称为操作)

我们把[l,r]代表当前处理的操作的区间,即处理第l个到第r个操作,先找到区间的中间m=(l+r)/2

(1)然后对于前一半[l,m]我们先递归解决。

(2)对于所有在[l,m]内的修改操作,枚举处理它对于[m,r]内的所有操作『影响』。

(3)之后递归处理[m,r]这一区间。

复杂度分析:分治共有log(n)层,那么要求每一层都在线性的时间复杂度内完成,才能保证总时间复杂度是O(nlogn)

对于不同的题目,修改和询问是不一样的。在某些修改之间互相独立的题目下,还可以调换(2)(3)的顺序。

当然cdq分治也可以想其他的分治方法一样,巧妙利用归并排序,来实现每层O(logn)

关于cdq分治 最经典的肯定就是三维偏序了

一句话 一维排序 一维cdq分治 一维树状数组 懂了就入门了

三位偏序:http://blog.csdn.net/cgh_andy/article/details/66971774

进阶:http://blog.csdn.net/cgh_andy/article/details/67633596

结合斜率优化:http://blog.csdn.net/cgh_andy/article/details/67633777

总的来说,整体二分就是将所有询问一起二分,然后获得每个询问的答案。

CDQ相比整体二分略有不同,整体二分是对答案进行二分,而CDQ分治则是对于所有操作进行二分。

其实这两个东西的思路差不多。。打起来也差不多。。

如果本蒟蒻有什么写的不好的 欢迎大家指出

当然有疑问你也可以问问本蒟蒻 虽说我不一定会
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: