zoukankan      html  css  js  c++  java
  • CF877F Ann and Books

    CF877F Ann and Books

    给定一个 01 序列,每次询问一个区间有多少个子区间其 1 的个数比 0 正好多 k 个,k 最初给定。

    我们可以做一遍前缀和,询问就相当于是在问两个前缀和的差等于 k 的有序对个数。

    于是我们每次单点修改的时候询问一下当前值 (sum+k) 或者 (sum-k) 这个桶个数即可,用哈希维护桶。

    代码:

    #pragma GCC optimize("Ofast")
    #pragma GCC optimize("unroll-loops")
    #pragma GCC target("sse,sse2,sse3,ssse3,sse4,popcnt,abm,mmx,avx,avx2,tune=native")
    #include<bits/stdc++.h>
    #include<ext/pb_ds/assoc_container.hpp>
    #include<ext/pb_ds/hash_policy.hpp>
    using namespace std;
    using namespace __gnu_pbds;
    template <typename T>
    inline void read(T &x){
    	x=0;char ch=getchar();bool f=false;
    	while(!isdigit(ch)){if(ch=='-'){f=true;}ch=getchar();}
    	while(isdigit(ch)){x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
    	x=f?-x:x;
    	return ;
    }
    template <typename T>
    inline void write(T x){
    	if(x<0) putchar('-'),x=-x;
    	if(x>9) write(x/10);
    	putchar(x%10^48);
    	return ;
    }
    const int N=1e5+5;
    #define ll long long
    int n,m,k;
    int bl[N],vis[N];
    ll a[N],Ans[N],pre[N];
    struct Query{int l,r,id;}Q[N];
    ll Now;
    gp_hash_table<long long,int>cnt;
    inline void Add(int x,bool f){
    	int y=k;
    	if(f) y=-k;
    	Now+=cnt[pre[x]+y];
    	cnt[pre[x]]++;
    	return ;
    }
    inline void Del(int x,bool f){
    	int y=k;
    	if(f) y=-k;
    	cnt[pre[x]]--;
    	Now-=cnt[pre[x]+y];
    	return ;
    }
    inline bool Cmp(Query x,Query y){return bl[x.l]^bl[y.l]?bl[x.l]<bl[y.l]:bl[x.l]&1?x.r<y.r:x.r>y.r;}
    int main(){
    	read(n),read(k);
    	for(int i=1;i<=n;i++) read(vis[i]);
    	for(int i=1;i<=n;i++){
    		read(a[i]);
    		if(vis[i]==1) pre[i]=pre[i-1]+a[i];
    		else pre[i]=pre[i-1]-a[i];
    	}
    	read(m);
    	const int t=sqrt(m);
    	for(int i=1;i<=m;i++) read(Q[i].l),read(Q[i].r),Q[i].id=i,Q[i].l--;
    	for(int i=1;i<=n;i++) bl[i]=(i-1)/t+1;
    	sort(Q+1,Q+m+1,Cmp);
    	int l=1,r=0;
    	for(int i=1;i<=m;i++){
    		while(l>Q[i].l) Add(--l,0);
    		while(r<Q[i].r) Add(++r,1);
    		while(l<Q[i].l) Del(l++,0);
    		while(r>Q[i].r) Del(r--,1);
    		Ans[Q[i].id]=Now;
    	}
    	for(int i=1;i<=m;i++) write(Ans[i]),putchar('
    ');
    	
    	return 0;
    } 
    
  • 相关阅读:
    数据库第三范式的思考
    channel通道例子
    go 测试代码性能实例
    go 新建項目引入gin失敗
    go 创建切片slice的四种方法
    Hibernate查询操作
    shell 分割训练数据
    hadoop streaming 分桶到不同的part
    C语言调用另一个文件的方法
    在springboot中使用jdbcTemplate(3)
  • 原文地址:https://www.cnblogs.com/Akmaey/p/14683271.html
Copyright © 2011-2022 走看看