树状数组BIT
2021-02-12 04:18
标签:span signed 适合 最大 记录 string 位置 区间 log 树状数组是利用数的二进制特征进行检索的树状结构 一般只适合对点进行更新O(logN),对区间进行查询O(logN) 对于源数据a[],c[]表示的时a[n-2^k+1]+a[n-2^k+2]+.....+a[n]的和,其中k为n在二进制下末尾0的个数,c[i]的覆盖范围长度时lowbit(i) 即i号位之前lowbit(i)位数的和 ,2^k=n and (n xor(n-1)) ,lowbit运算时根据n的值返回2^k 操作: (1)修改元素add(k,x),把ak加上x (2)求和sum(x),sum(x)=x1+x2+...+xx,然后ai+...+aj=sum(j)-sum(i-1) 重要操作:lowbit(x) x&(-x),这个操作时找到x的二进制数的最后一个1,原理是利用了负数的补码表示,补码是原码取反加1 (1)#define lowbit(x) ((x)&(-x)) lowbit(x)也可以理解为能够整除x的最大2的幂次! (2)int lowbit(int x){ return x&(x^(x-1)); } 令m=lowbit(x),定义tree[x]的值,是把ax和它前面的共m个数相加的结果 应用 1:给出一个序列,和一系列查询,每次查询前i个数的总和,但是同时会在第x个数上增加v,这样每次查询的结果都会变化(在线查询) 树状数组:lowbit[]数组,记录在i号位之前(包含i号)lowbit(i)个数的和,(ps;下标必须从1开始) 最经典应用:给定一个有n个正整数的序列A,对序列中的每个数,求出它左边比他小的数的个数 特殊情况下改进: 例题:POJ 2182 Lost Cows 题目大意:有n头牛,给出从第二头牛开始每头牛前面有多少头牛编号比自己小。 求牛的编号。 分析:每次最后一头牛的编号为当前可用编号中排在第a[i]+1的数。 这道题的特殊在于:1、不需要用add()初始化,因为lowbit(i)就是tree[i] 2、对每个pre[i]+1,用findpos()二分找出sum(x)=pre[i]+1所对应的x,就是第x头牛 这道题的线段树做法 树状数组BIT 标签:span signed 适合 最大 记录 string 位置 区间 log 原文地址:https://www.cnblogs.com/shirlybaby/p/12732241.htmlint lowbit(int x){
return x&(x^(x-1));
}
//查询,查询一个区间的和
//sum[1,x]=sum(1,x-lowbit(x))+c[x]
int summ(int x){
int summ=0;
while(x>0){
sum+=c[x];
x-=lowbit(x);
}
}
//更新,对一个数据进行更改
void upda(int index,int num){
while(index0){
int temp=j;
while(temp>0){
summ+=c[i][temp];
temp-=lowbit(temp);
}
i-=lowbit(i);
}
return summ;
}
int c[maxn]; //记录在i号位之前(包含i号)lowbit(i)个数的和,
int getsum(int k){ //返回前k位数据之和
int sum=0;
for(int i=k;i>0;i-=lowbit(i)){
sum+=c[i]; //c[i]记录的本来就输若干个a[i]的和,所以可直接累加
}
return sum;
}
void update(int x,int v){ //在第x个数据上加上v
for(int i=x;i
只需要把update的含义改变一下即可:x出现的次数加1
eg:如果统计元素右边比它大的数据个数:getsum(n)-getsum(a[i])即可
eg:如果统计元素左边比它大的数据个数(右边比它小):从右往左遍历即可 void js(){
int n,d;
cin>>n;
memset(c,0,sizeof(c));
for(int i=1;i>d;
update(d,1,n); //d出现的次数加1
cout
A[i]
跟计算排名问题相似:根据值从小到大排名,如果成绩一样,排名也一样
利用结构体存储原本的数据和原始下标,再用另一个数组存储他们的排名,在这个数组的基础上计算struct node{
int val; //会超过存储大小的实际的值
int index; //原本的下标
}temp[maxn];
int a[maxn];
int cc[maxn]; //记录在i号位之前(包含i号)lowbit(i)个数的和
bool cmp(node a,node b){
return a.val
#include
#include
上一篇:四、线程组-调度器配置