• "美登杯" E、小花梨的数组* 线段树


    操作过程中标记传递  询问的时候再计算

    #include<bits/stdc++.h>
    using namespace std;
    //input by bxd
    #define rep(i,a,b) for(int i=(a);i<=(b);i++)
    #define repp(i,a,b) for(int i=(a);i>=(b);--i)
    #define RI(n) scanf("%d",&(n))
    #define RII(n,m) scanf("%d%d",&n,&m)
    #define RIII(n,m,k) scanf("%d%d%d",&n,&m,&k)
    #define RS(s) scanf("%s",s);
    #define ll long long
    #define pb push_back
    #define CLR(A,v)  memset(A,v,sizeof A)
    //////////////////////////////////
    #define inf 0x3f3f3f3f
    #define lson l,m,pos<<1
    #define rson m+1,r,pos<<1|1
    const int N=100000+5;
    const int mod=1e9+7;
    int f[N*10],prime[N*10],pre[N*10],cnt;
    
    void init()
    {
        f[1]=1;
        prime[0]=prime[1]=1;
        rep(i,2,1e6)
        {
            if(prime[i]==0)
            {
                pre[++cnt]=i;
                f[i]=i;
            }
            for(int j=1;j<=cnt&&pre[j]*i<=1e6;j++)
            {
                prime[i*pre[j]]=1;
                f[i*pre[j]]=pre[j];
                if(i%pre[j]==0)break;
            }
        }
    }
    
    ll fast(ll x,ll n)
    {
        ll ans=1;
        while(n)
        {
            if(n&1)ans=(ans*x)%mod;
            x*=x;x%=mod;
            n>>=1;
        }
        return ans%mod;
    }
    
    ll sum[N<<2],col[N<<2];
    
    void up(int pos)
    {
        sum[pos]=sum[pos<<1]+sum[pos<<1|1];
    }
    
    void down(int pos)
    {
        col[pos<<1]+=col[pos];
        col[pos<<1|1]+=col[pos];
        col[pos]=0;
    }
    
    void build(int l,int r,int pos)
    {
        if(l==r)
        {
            scanf("%lld",&sum[pos]);col[pos]=0;
            return ;
        }
        int m=(l+r)>>1;
        build(lson);build(rson);
        up(pos);
    }
    
    
    void update1(int L,int R,int l,int r,int pos)
    {
        if(sum[pos]==r-l+1)return ;
        if(L<=l&&r<=R)
        {
            col[pos]++;
            return ;
        }
        down(pos);
        int m=(l+r)>>1;
        if(L<=m)update1(L,R,lson);
        if(R>m)update1(L,R,rson);
        up(pos);
    }
    
    void update2(int L,int R,int l,int r,int pos)
    {
        if(sum[pos]==r-l+1)return ;
    
        if(L<=l&&r<=R&&col[pos])
        {
            col[pos]--;return ;
        }
        if(l==r)
        {
            sum[pos]=sum[pos]/f[sum[pos]]%mod;return ;
        }
        down(pos);
        int m=(l+r)>>1;
        if(L<=m)update2(L,R,lson);
        if(R>m)update2(L,R,rson);
        up(pos);
    }
    
    ll query(int x,int l,int r,int pos)
    {
        if(sum[pos]==r-l+1)return 1;
        if(l==r)
        {
            return  sum[pos]*fast(f[sum[pos]],col[pos])%mod;
        }
        down(pos);
        int m=(l+r)>>1;
        if(x<=m)return query(x,lson);
        else return query(x,rson);
    }
    
    int main()
    {
        init();
        int n,m;
        RII(n,m);
        build(1,n,1);
        int q,a,b;
        while(m--)
        {
            RI(q);
            if(q==1)
            {
                RII(a,b);
                update1(a,b,1,n,1);
            }
            else if(q==2)
            {
                RII(a,b);
                update2(a,b,1,n,1);
            }
            else if(q==3)
            {
               RI(a);cout<<query(a,1,n,1)<<endl;
            }
        }
        return 0;
    }
    View Code
  • 相关阅读:
    python 垃圾回收装置
    文件夹同步/备份软件推荐 (SyncToy/FreeFileSync/Compare Advance/GoodSync/Allway Sync/Compare Advance)
    WCF的ABC
    NPOI导出多表头Execl(通过html表格遍历表头)
    分布式应用处理方式
    再探ASP.NET 5(转载)
    应聘.net开发工程师常见的面试题(五)
    应聘.net开发工程师常见的面试题(四)
    应聘.net开发工程师常见的面试题(二)(转载)
    应聘.net开发工程师常见的面试题(一)(转载)
  • 原文地址:https://www.cnblogs.com/bxd123/p/10890618.html
Copyright © 2020-2023  润新知