这题虽然是个树状数组,但是也可以用cdq分治做啊~~,这个就是一个浅显的二维偏序的应用?

cdq分治和普通的分治有什么区别?

举个栗子:有4个小朋友,你请他们吃饭,假如你分治搞,就会分成很多子问题——1~1号小朋友有多少个来,2~2号小朋友有多少个来,然后程序就会回溯,你就知道1~2号小朋友有多少个来,最后你就知道1~4号小朋友有多少个来了。

而cdq分治呢?同样是4个小朋友,但是要照顾小朋友的心情,第i号小朋友的开心程度是1~i-1号小朋友有多少个来,你想知道小朋友们的心情,有可能心情不好就不来了,那先往左右搜,然后要把心情的影响加上。可能这个栗子不是很贴切,但是我想说的就是cdq分治中,前面的结果会影响后面的,而且,这个算法做题只能离线。

那么,我是拿了这题水题来理解。

俩操作,一个单点修改,一个询问区间和。

那么我们还是照样按前缀和的做法,把询问分成求1~l-1和1~r。

那么离线做,按照输入的顺序放进结构体,这个时候你一定发现了,对于一个询问,对它有影响的修改,就是在它前面操作的,并且修改位置也在它询问位置前面的。那么,实际上这个结构体已经是按照操作的顺序排好了,那么要解决的就是位置的问题。具体的做法,就是按照它的位置,做一次归并排序。

具体怎么做呢,首先先把区间分成l~mid和mid+1~r,当前我们要维护的,就是mid+1~r的全部询问,要先让两边都递归下去,令l~mid的询问解决,以及mid+1~r里的修改施加影响。

那么在归并的过程中,记录一个sum,表示左边已经l~当前归并到的位置的修改值的和,然后当遇到右边的询问,就将影响释放下去,一直这样做下去,当按x排好序了,对于mid+1~r中的询问,l~r的全部影响都已经解决,最后回溯接受更前面的影响,或者去影响后面的其他询问(你这样归排岂不是把一开始操作的顺序打乱了!?不用担心,l~mid的输入顺序每一个都是比mid+1~r大的,l~mid的顺序改变并不会影响后面的修改)

#include<cstdio>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<algorithm>
#include<cmath>
using namespace std;
typedef long long LL; int n,m;
struct node
{
int x,tp;LL v;
//tp=1表示这个是修改操作,x表示修改哪个位置,v表示要加上的值
//tp=2,3表示这个是问1~x的前缀和,v表示这个影响第几个答案
}a[],t[];int len=;
void ins(int x,int tp,int v)
{
len++;
a[len].x=x;a[len].tp=tp;a[len].v=v;
}
LL ans[];int ansl=;//答案数组
bool check(node n1,node n2)
{
if(n1.x<n2.x||(n1.x==n2.x&&n1.tp<n2.tp))return true;
return false;
}
void cdq(int l,int r)
{
if(l==r)return ;
int mid=(l+r)/;
cdq(l,mid);cdq(mid+,r); LL sum=;//sum表示l~t[p].x的修改的和
int i=l,j=mid+,p=l;
while(i<=mid&&j<=r)
{
if(check(a[i],a[j])==true)//只统计左边区间内的修改值,因为右边的修改值已经在递归里影响过了
{
if(a[i].tp==)sum+=a[i].v;
t[p++]=a[i++];
}
else//将左边的影响影响右边
{
if(a[j].tp==)ans[a[j].v]-=sum;
else if(a[j].tp==)ans[a[j].v]+=sum;
t[p++]=a[j++];
}
}
while(i<=mid)t[p++]=a[i++];
while(j<=r)
{
if(a[j].tp==)ans[a[j].v]-=sum;
else if(a[j].tp==)ans[a[j].v]+=sum;
t[p++]=a[j++];
} for(int i=l;i<=r;i++)a[i]=t[i];
} char ss[];
int main()
{
int x,l,r;LL v;
scanf("%d%d",&n,&m);
for(int i=;i<=m;i++)
{
scanf("%s",ss+);
if(ss[]=='C')
{
scanf("%d%lld",&x,&v);
ins(x,,v);
}
else//利用前缀和的思想,把查询操作分为两部分
{
scanf("%d%d",&l,&r);
ansl++;ins(l-,,ansl);ins(r,,ansl);
}
}
cdq(,len);
for(int i=;i<=ansl;i++)printf("%lld\n",ans[i]);
return ;
}

caioj1097: [视频]树状数组1(快速求和计算) cdq分治入门的更多相关文章

  1. poj 1195:Mobile phones(二维树状数组,矩阵求和)

    Mobile phones Time Limit: 5000MS   Memory Limit: 65536K Total Submissions: 14489   Accepted: 6735 De ...

  2. HRBUST 1161 树状数组区间更新求和

    Leyni Time Limit: 3000 MS Memory Limit: 65536 K Total Submit: 267(64 users) Total Accepted: 82(57 us ...

  3. P3374 【模板】树状数组 1

    树状数组模板题,用cdq分治做 cdq分治: 分:把l到r分成两个区间操作 治:对每个分出来的区间进行操作 但是cdq分治和一般分治不同的是,一般的分治左右两个区间互不干扰,但是cdq分治处理的是区间 ...

  4. 【bzoj3262】陌上花开 CDQ分治+树状数组

    题目描述 有n朵花,每朵花有三个属性:花形(s).颜色(c).气味(m),又三个整数表示.现要对每朵花评级,一朵花的级别是它拥有的美丽能超过的花的数量.定义一朵花A比另一朵花B要美丽,当且仅当Sa&g ...

  5. 【牛客小白月赛6】F 发电 - 树状数组&快速幂&逆元

    题目地址:https://www.nowcoder.com/acm/contest/136/F 树状数组.快速幂.逆元的模板运用: #include<iostream> #include& ...

  6. HH的项链题解(离线思想+链表+树状数组)

    本人第一篇博客重磅推出!!! 希望各位朋友以后多多捧场也多给写意见(我个人喜欢把题解写得啰嗦一点,因为这样方便理解,各位巨佬勿喷) 来讲一道提高+/省选-的骚题:HH的项链(这个HH你理解成皇后呵呵哈 ...

  7. 树状数组求第k小的元素

    int find_kth(int k) { int ans = 0,cnt = 0; for (int i = 20;i >= 0;i--) //这里的20适当的取值,与MAX_VAL有关,一般 ...

  8. POJ 1990 MooFest(树状数组)

                                                                        MooFest Time Limit: 1000MS   Mem ...

  9. HDU 2689Sort it 树状数组 逆序对

    Sort it Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Sub ...

随机推荐

  1. 更换SpringBoot中默认的web容器为jetty

    在pom文件中:<dependency> <groupId>org.springframework.boot</groupId> <artifact>s ...

  2. ASP.NET Core on K8S学习初探(1)K8S单节点环境搭建

    当近期的一个App上线后,发现目前的docker实例(应用服务BFF+中台服务+工具服务)已经很多了,而我司目前没有专业的运维人员,发现运维的成本逐渐开始上来,所以容器编排也就需要提上议程.因此我决定 ...

  3. Haproxy配置文件详解

    #/usr/local/sbin/haproxy -f /etc/haproxy/haproxy.cfg -st `cat /var/run/haproxy.pid` ################ ...

  4. luogu2468 [SDOI2010]粟粟的书架

    二合一-- #include <iostream> #include <cstdio> using namespace std; int r, c, m, a[205][205 ...

  5. sprintboot + mybaits + mysql + html5 + thymeleaf 个人笔记

    参考:https://github.com/daleiwang/moxi service @Mapper 与 @Select 等 @Mapper似乎是一个myBaits 注解,表示将java方法和sq ...

  6. 公路修建(Prim)

    洛谷传送门 这道水题告诉了我,堆优化的prim有时还不如朴素prim快... 居然记错时间复杂度了,我也真是菜. #include <cstdio> #include <queue& ...

  7. Android资源目录结构

    资源目录结构 res为资源目录,主要以xml语法编写静态的资源. 资源的命名标准:小写字母和数字,且以小写字母开头. 资源的生成,为了和java语法沟通,资源文件会自动的生成在[gen]目录的R.ja ...

  8. php 以单下划线或双下划线开头的命名

    有2个下划线的是魔术方法,如:__construct.__destruct等等.有1个下划线的一般是私有方法,如 _initialize. 小测试: public function _test(){ ...

  9. Python()- 面向对象三大特性----多态

    多态: python 生来支持多态白话:一种事物的多种形态 (动物可以继承给狗,也可以继承给猫) class Animal: pass class Dog(Animal): def attack(se ...

  10. 混合APP开发框架资料汇总

    Ionic(ionicframework)一款接近原生的Html5移动App开发框架 会html css js就可以开发app,Ionic基于angualrjs框架是一个专注于开发移动wap以及app ...