之前听大神讲过CDQ分治大概是个什么东西,但是一直还没有真正去搞过。今天稍微看了一下,写点自己的理解。

首先CDQ分治有两个条件。

条件1:可以分成两个独立互不影响的问题(这里的“独立”是指将前面区间的影响处理掉后,后面与前面都成为了新的相同问题)

条件2:允许离线(据说最近流行强制在线。。。如果这样只好去写恶心的数据结构了)。

CDQ分治在可以使用的情况下很多高级数据结构题可以用CDQ分治干过去,不仅时空优越而且易于调试(虽然我并不觉得很好调试

大体思路是将问题不断分成两个子问题,用前一个子问题中的修改操作去更新后一个子问题,这样之后就得到了两个互不影响的子问题,达到分治的目的。

贴一道版题代码:BZOJ 1176

 #include<bits/stdc++.h>
using namespace std;
#define lowbit(x) ((x)&-(x))
struct data{
int v,x,y,d,f,pos;
bool operator <(const data& w)const{
if(x!=w.x) return x<w.x;
if(y!=w.y) return y<w.y;
return pos<w.pos;
}
}a[],tmp[];
int s,w,t[],cnt,ans[];
int read(int& x){
x=; int f=,a=getchar();
while(a<'' || a>'') {if(a=='-') f=-; a=getchar();}
while(a>='' && a<='') x=x*+a-'',a=getchar(); x*=f;
}
inline void add(int y,int x){for(int i=y;i<=w;i+=lowbit(i)) t[i]+=x;}
inline int query(int y){int ret=; for(int i=y;i;i-=lowbit(i)) ret+=t[i]; return ret;}
void CDQ(int l,int r){
if(l==r) return;
int mid=(l+r)>>,t1=l-,t2=mid; //这里写错调了老半天
for(int i=l;i<=r;i++){
if(a[i].v<=mid && !a[i].pos) add(a[i].y,a[i].d);
if(a[i].v>mid && a[i].pos) ans[a[i].pos]+=query(a[i].y)*a[i].f;
}
for(int i=l;i<=r;i++)
if(a[i].v<=mid && !a[i].pos) add(a[i].y,-a[i].d);
for(int i=l;i<=r;i++)
if(a[i].v<=mid) tmp[++t1]=a[i];
else tmp[++t2]=a[i];
for(int i=l;i<=r;i++) a[i]=tmp[i];
CDQ(l,mid); CDQ(mid+,r);
}
int main(){
read(s); read(w); int t,x,y,d,x1,x2,y1,y2;
while(){
read(t);
if(t==){
read(x); read(y); read(d);
a[++cnt]=(data){cnt,x,y,d,,};
}else if(t==){
read(x1); read(y1); read(x2); read(y2); ++ans[];
a[++cnt]=(data){cnt,x1-,y1-,,,ans[]};
a[++cnt]=(data){cnt,x2,y2,,,ans[]};
a[++cnt]=(data){cnt,x1-,y2,,-,ans[]};
a[++cnt]=(data){cnt,x2,y1-,,-,ans[]};
}else break;
}
sort(a+,a++cnt);
CDQ(,cnt);
for(int i=;i<=ans[];i++)
printf("%d\n",ans[i]);
return ;
}

胡扯两句——CDQ分治的更多相关文章

  1. Hdu5126-stars(两次CDQ分治)

    题意: 简化就是有两种操作,一种是插入(x,y,z)这个坐标,第二种是查询(x1,y1,z1)到(x2,y2,z2)(x1<=x2,y1<=y2,z1<=z2)的长方体包含多少个点. ...

  2. 【Luogu1393】动态逆序对(CDQ分治)

    [Luogu1393]动态逆序对(CDQ分治) 题面 题目描述 对于给定的一段正整数序列,我们定义它的逆序对的个数为序列中ai>aj且i < j的有序对(i,j)的个数.你需要计算出一个序 ...

  3. cdq分治的小结

    cdq分治 是一种特殊的分治 他的思想: 1.分治l,mid 2.分治mid+1,r 3.计算l,mid对mid+1,r的影响 3就是最关键的地方 这也是cdq的关键点 想到了这一步基本就可以做了 接 ...

  4. 【洛谷3157】[CQOI2011] 动态逆序对(CDQ分治)

    点此看题面 大致题意: 给你一个从\(1\)到\(n\)的排列,问你每次删去一个元素后剩余的逆序对个数. 关于\(80\)分的树套树 为了练树套树,我找到了这道题目. 但悲剧的是,我的 线段树套\(T ...

  5. luogu P3157 [CQOI2011]动态逆序对(CDQ分治)

    题目描述 对于序列A,它的逆序对数定义为满足i<j,且Ai>Aj的数对(i,j)的个数.给1到n的一个排列,按照某种顺序依次删除m个元素,你的任务是在每次删除一个元素之前统计整个序列的逆序 ...

  6. CDQ分治题目小结

    CDQ分治属于比较特殊的一类分治,许多问题转化为这类分治的时候,时空方面都会有很大节省,而且写起来没有这么麻烦. 这类分治的特殊性在于分治的左右两部分的合并,作用两部分在合并的时候作用是不同的,比如, ...

  7. [学习笔记] CDQ分治 从感性理解到彻底晕菜

    最近学了一种叫做CDQ分治的东西...用于离线处理一系列操作与查询似乎跑得很快233 CDQ的名称似乎源于金牌选手陈丹琦 概述: 对于一坨操作和询问,分成两半,单独处理左半边和处理左半边对于右半边的影 ...

  8. $CDQ$分治总结

    A.\(CDQ\) 分治 特别基础的教程略. \(CDQ\)分治的优缺点: ( 1 )优点:代码量少,常数极小,可以降低处理维数. ( 2 )缺点:必须离线处理. \(CDQ\)分治与其他分治最本质的 ...

  9. BZOJ1173 CDQ分治 笔记

    目录 二维数据结构->cdq 预备知识 T1: 二维树状数组 T2:cdq分治 bzoj1176 mokia:Debug心得 一类特殊的CDQ分治 附: bzoj mokia AC代码 二维数据 ...

随机推荐

  1. Redis主从配置详细过程

    Redis的主从复制功能非常强大,一个master可以拥有多个slave,而一个slave又可以拥有多个slave,如此下去,形成了强大的多级服务器集群架构.下面楼主简单的进行一下配置. 1.上面安装 ...

  2. [转载] 为 Key-Value 数据库实现 MVCC 事务

    http://mp.weixin.qq.com/s?__biz=MzA5ODM5MDU3MA==&mid=400086920&idx=1&sn=b8174184059e2886 ...

  3. Java 13 字符串

    1 String对象不可变 每一个修改String值的方法 实际上都是创建一个全新的String对象 public class Immutable { public static String upc ...

  4. iOS开发之总结

    NO.1 要孜孜不倦的学习有句话叫技多不压身,编程本来就是一个更新换代非常快的工作.每年都有新的技术出现,我认为要成为一个出色的程序员只掌握一门语言肯定是不行的.那么,要怎么选择自己的第二门,甚至第三 ...

  5. Nexus中自定义私服,每个项目都用独立的工厂,仓库

    原文:http://blog.csdn.net/mexican_jacky/article/details/50278045 第一步:创建工厂仓库 第二步:cms项目,那么我们就只能cms项目组用,那 ...

  6. QBC用法

    方法 说明 Restrictions.eq = Restrictions.allEq 利用Map来进行多个等于的限制 Restrictions.gt > Restrictions.ge > ...

  7. OpenGL的glPushMatrix和glPopMatrix矩阵栈顶操作函数详解

    OpenGL中图形绘制后,往往需要一系列的变换来达到用户的目的,而这种变换实现的原理是又通过矩阵进行操作的.opengl中的变换一般包括视图变换.模型变换.投影变换等,在每次变换后,opengl将会呈 ...

  8. Sqlserver_insert语法

    1. INSERT INTO SELECT 通过 SQL,您可以从一个表复制信息到另一个表.   INSERT INTO SELECT 语句从一个表复制数据,然后把数据插入到一个已存在的表中. 我们可 ...

  9. 删除github账号的方法

    如果你不想使用自己的github账号了,github官网允许你删除账号,具体操作步骤为: 1.登录github网站,网站右上角的头像,在下拉菜单中选择"Settings"(设置): ...

  10. LTIB常用命令3

    http://blog.csdn.net/junht/article/details/7656540 LTIB 中的包 4.3.1  查看哪些包是使能的,并且可以安装 在配置ltib之前,您可以在一个 ...