BZOJ1901: Zju2112 Dynamic Rankings
2016-10-17 16:37
429 查看
发现还是不怎么会整体二分,学一道模版
将初始的序列的视为将第i个位置改为a[i]的操作,和所有操作放在一起
二分一个值,将所有操作里值不大于二分值的在树状数组里的位置+1,下放到右边,大于的下放到左边,对于询问,如果区间里的数≥k,将这个操作下放到左区间,否则下放到右区间,将k减去询问的值(因为这些左区间的操作以后不会再考虑),然后在树状数组里撤销之前的操作,向下二分
code:
将初始的序列的视为将第i个位置改为a[i]的操作,和所有操作放在一起
二分一个值,将所有操作里值不大于二分值的在树状数组里的位置+1,下放到右边,大于的下放到左边,对于询问,如果区间里的数≥k,将这个操作下放到左区间,否则下放到右区间,将k减去询问的值(因为这些左区间的操作以后不会再考虑),然后在树状数组里撤销之前的操作,向下二分
code:
#include<set> #include<map> #include<deque> #include<queue> #include<stack> #include<cmath> #include<ctime> #include<bitset> #include<string> #include<vector> #include<cstdio> #include<cstdlib> #include<cstring> #include<climits> #include<complex> #include<iostream> #include<algorithm> #define ll long long #define inf 1e9 using namespace std; const int maxn = 41000; struct node { int l,r,c,s,id; node(){} node(int a1,int a2,int a3,int a4,int a5){l=a1;r=a2;c=a3;s=a4;id=a5;} }a[maxn],b[maxn],br[maxn]; int num; int n,m; int s[maxn],ans[maxn],nw[maxn]; int lowbit(int x){return x&(-x);} void add(int x,int c){ while(x<=n){s[x]+=c;x+=lowbit(x);} } int query(int x){int ret=0;while(x>0){ret+=s[x];x-=lowbit(x);}return ret;} void solve(int lp,int rp,int lc,int rc) { if(lp>rp)return; if(lc==rc) { for(int i=lp;i<=rp;i++) if(a[i].s==2)ans[a[i].id]=lc; return ; } int mid=(lc+rc)>>1; int bn=0,brn=0; for(int i=lp;i<=rp;i++) { if(a[i].s<2) { if(a[i].c<=mid) { b[++bn]=a[i]; add(a[i].l,a[i].s==0?1:-1); } else br[++brn]=a[i]; } else { int temp=query(a[i].r)-query(a[i].l-1); if(temp>=a[i].c)b[++bn]=a[i]; else { br[++brn]=a[i];br[brn].c-=temp; } } } for(int i=lp;i<=rp;i++) if(a[i].s<2) { if(a[i].c<=mid)add(a[i].l,a[i].s==0?-1:1); } for(int i=1;i<=bn;i++)a[lp+i-1]=b[i]; for(int i=1;i<=brn;i++)a[lp+bn+i-1]=br[i]; solve(lp,lp+bn-1,lc,mid); solve(lp+bn,rp,mid+1,rc); } int main() { char str[10]; scanf("%d%d",&n,&m);num=0; for(int i=1;i<=n;i++) { int x;scanf("%d",&x);nw[i]=x; a[++num]=node(i,i,x,0,0); } for(int i=1;i<=m;i++) { scanf("%s",str); if(str[0]=='Q') { int l,r,k;scanf("%d%d%d",&l,&r,&k); a[++num]=node(l,r,k,2,i); } else { int l,k;scanf("%d%d",&l,&k); a[++num]=node(l,l,nw[l],1,0); a[++num]=node(l,l,k,0,0); nw[l]=k; } } for(int i=1;i<=m;i++)ans[i]=-1; solve(1,num,0,inf); for(int i=1;i<=m;i++)if(ans[i]!=-1)printf("%d\n",ans[i]); return 0; }
相关文章推荐
- [BZOJ]1901: Zju2112 Dynamic Rankings 主席树
- BZOJ 1901 Zju2112 Dynamic Rankings ——树状数组套主席树
- 【题解】BZOJ 1901: Zju2112 Dynamic Rankings
- bzoj 1901: Zju2112 Dynamic Rankings (树状数组套线段树)
- BZOJ 1901 Zju2112 Dynamic Rankings ——整体二分
- [Bzoj1901]Zju2112 Dynamic Rankings
- [Bzoj1901]Zju2112 Dynamic Rankings
- 【BZOJ 1901】【Zju 2112】 Dynamic Rankings 动态K值 树状数组套主席树模板题
- BZOJ1901 Zju2112 Dynamic Rankings 【树状数组套主席树】
- [BZOJ1901][ZJU2112]Dynamic Rankings
- bzoj 1901: Zju2112 Dynamic Rankings(树套树)
- bzoj 1901: Zju2112 Dynamic Rankings
- bzoj 1901: Zju2112 Dynamic Rankings 树状数组套线段树 cdq分治
- BZOJ[1901]Zju2112 Dynamic Rankings 树套树(线段树套Splay)
- 【BZOJ 1901】 Zju2112 Dynamic Rankings|树状数组套主席树
- BZOJ 1901: Zju2112 Dynamic Rankings( BIT 套 BST )
- 【bzoj1901】Zju2112 Dynamic Rankings 线段树套平衡树
- BZOJ 1901 Zju2112 Dynamic Rankings
- bzoj 1901: Zju2112 Dynamic Rankings(树套树)
- BZOJ1901: Zju2112 Dynamic Rankings