• 洛谷 P5358 [SDOI2019]快速查询


    题目链接

    学习线段树的区间懒标记想法,我们把整个区间当作一个区间。

    懒标记有(add,mul,cov)

    (add):区间里每个数加上多少。
    (mul):区间里每个数乘上多少。
    (cov):最近一次区间赋值的值是多少。

    利用上面三个标记,我们就解决了所有区间修改。

    但是单点修改呢?

    题目中操作种数只有(10^5)种,因此所有单点可以单独提取出来离散化一下。

    我们考虑单点赋值,赋值后这个点就符合我们上面的懒标记了,所以我们要把这个值改造一下。

    最后单点值(V_i = (a_i + cov) * mul + add)

    然后就可以了。

    
    #include<bits/stdc++.h>
    using namespace std;
    
    const int mod = 1e7 + 19;
    
    int n,Q,t;
    struct Que{
        int opt;
        int id; long long val,inv;
    }q[100050];
    
    int lsh[100050],ccnt;
    
    long long totsum, totadd, totmul, totinv;
    long long cov;
    long long temp[100050];
    
    bitset<100050> use;
    int U[100050],cnt;
    
    //(temp_i + cov) * totmul + totadd = val_i
    
    long long ksm(long long x,long long y){
        long long z = 1;
        while(y){
            if(y & 1) z = z * x % mod;
            y >>= 1;
            x = x * x % mod;
        }
        return z;
    }
    
    long long Ans;
    
    void work(int idx){
        if(q[idx].opt == 1){
        	long long tmp = temp[q[idx].id];
        	tmp += cov; tmp %= mod;
        	tmp *= totmul; tmp %= mod;
        	tmp += totadd; tmp %= mod;
        	tmp = (tmp % mod + mod) % mod;
        	
        	totsum += q[idx].val - tmp; totsum = (totsum % mod + mod) % mod;
        	
        	tmp = q[idx].val;
        	tmp -= totadd; tmp += mod; tmp %= mod;
        	tmp *= totinv; tmp %= mod;
        	tmp -= cov; tmp += mod; tmp %= mod;
        	temp[q[idx].id] = tmp;
        	
        	if(!use[q[idx].id]) { use[q[idx].id] = 1; U[++ cnt] = q[idx].id; }
        }
        if(q[idx].opt == 2){
        	totadd += q[idx].val; totadd %= mod;
        	totsum += 1ll * n * q[idx].val % mod; totsum %= mod;
        }
        if(q[idx].opt == 3){
        	totmul = totmul * q[idx].val % mod; totinv = totinv * q[idx].inv % mod;
        	totadd = totadd * q[idx].val % mod; 
        	totsum = totsum * q[idx].val % mod;
        }
        if(q[idx].opt == 4){
        	totmul = 1; totadd = 0; totinv = 1;
        	cov = q[idx].val; while(cnt) { temp[U[cnt]] = 0; -- cnt; } use.reset();
        	totsum = 1ll * n * q[idx].val % mod;
        }
        if(q[idx].opt == 5){
        	long long tmp = temp[q[idx].id];
        	tmp += cov; tmp %= mod;
        	tmp *= totmul; tmp %= mod;
        	tmp += totadd; tmp %= mod;
        	tmp = (tmp % mod + mod) % mod;
        	Ans += tmp; Ans %= mod;
        	//printf("%lld
    ",tmp);
        }
        if(q[idx].opt == 6){
        	totsum = (totsum % mod + mod) % mod;
            Ans += totsum; Ans %= mod;
            //printf("%lld
    ",totsum);
        }
    }
    
    int main(){
    	scanf("%d%d",&n,&Q); n %= mod;
    	for(int i = 1; i <= Q; ++ i){
    	    scanf("%d",&q[i].opt);
    	    if(q[i].opt == 1) scanf("%d%lld",&q[i].id,&q[i].val);
    	    else if(q[i].opt <= 4) scanf("%lld",&q[i].val);
    	    else if(q[i].opt == 5) scanf("%d",&q[i].id);
    	    q[i].val = (q[i].val % mod + mod) % mod;
    	    if(q[i].opt == 3) q[i].inv = ksm(q[i].val, mod - 2);
    	}
    	for(int i = 1; i <= Q; ++ i){
    	    if(q[i].opt == 1 || q[i].opt == 5) lsh[++ ccnt] = q[i].id;
    	}
    	sort(lsh + 1, lsh + ccnt + 1); ccnt = unique(lsh + 1, lsh + ccnt + 1) - lsh - 1;
    	for(int i = 1; i <= Q; ++ i){
    	    if(q[i].opt == 1 || q[i].opt == 5) q[i].id = lower_bound(lsh + 1, lsh + ccnt + 1, q[i].id) - lsh;
    	}
    	
    	totsum = 0; totmul = 1; totinv = 1; totadd = 0; cov = 0; memset(temp,0,sizeof(temp));
    	Ans = 0; use.reset(); cnt = 0;
    	
    	scanf("%d",&t);
    	for(int i = 0; i < t; ++ i){
    	    int a,b; scanf("%d%d",&a,&b);
    	    long long op = a;
    	    for(int j = 1; j <= Q; ++ j){
    	        op += b; op %= Q; 
    	        work(op + 1);
    	    }
    	}
    	printf("%lld
    ",Ans);
    	return 0;
    }
    
    
  • 相关阅读:
    SpringCloudAlibaba
    SpringCloudAlibaba
    SpringCloudAlibaba
    SpringCloudAlibaba
    SpringCloudAlibaba
    SpringCloudAlibaba
    SpringCloudAlibaba
    SpringCloudAlibaba
    如何使用webify快速构建Nuxt应用
    “我,不懂代码,36岁转行开发”
  • 原文地址:https://www.cnblogs.com/zzhzzh123/p/13386096.html
Copyright © 2020-2023  润新知