#10 TLE求调
查看原帖
#10 TLE求调
866144
holo_23楼主2024/12/5 19:26
#include "iostream"
#include "vector"
#include "utility"
#define ll long long
using namespace std;
typedef struct tree_node{
    ll l,r;
    ll sum,add,sum_sq;
};

tree_node tree[400010];
ll nums[100010];
int mod=1e9+7;


void push_up(int p){
    tree[p].sum= (tree[p*2].sum+tree[p*2+1].sum);
    tree[p].sum_sq= (tree[p*2].sum_sq+tree[p*2+1].sum_sq);
}

void build_tree(ll l,ll r,ll p){
    tree[p].l=l;
    tree[p].r=r;
    if(l==r){
        tree[p].sum=nums[l];
        tree[p].sum_sq=nums[l]*nums[l];
        return;
    }
    ll mid= (l+r)/2;
    build_tree(l,mid,p*2);
    build_tree(mid+1,r,p*2+1);
    push_up(p);
   
}


void update_add(ll t,ll d,ll p){
    ll r=tree[p].r,l=tree[p].l;
    if(t==l && r==t){
        tree[p].sum=d;
        tree[p].sum_sq=d*d %mod;
        return;
    }
    ll mid=(l+r)/2;
    if(t<=mid){
        update_add(t,d,p*2);
    }
    else{
        update_add(t,d,p*2+1);
    }
    push_up(p);
}

pair<ll,ll> get_sum(ll target_l,ll target_r,ll p){
    ll r=tree[p].r,l=tree[p].l;
    if(l>=target_l && r<=target_r){
        return make_pair(tree[p].sum,tree[p].sum_sq);
    }
    ll mid=(l+r)/2;
    if(target_r<=mid){
        return get_sum(target_l,target_r,p*2);
    }
    if(target_l>mid){
        return get_sum(target_l,target_r,p*2+1);
    }
    return make_pair(get_sum(target_l,mid,p*2).first+get_sum(mid+1,target_r,p*2+1).first,get_sum(target_l,mid,p*2).second+get_sum(mid+1,target_r,p*2+1).second);
}

ll get_mul_inverse(ll x,ll p=mod-2){
    ll res=1;
    // x^p =1
    while(p){
        if(p&1){
            res=(res*x)%mod;
        }
        x=x*x%mod;
        p>>=1;
    }
    return res;
 
}

ll get_ans(pair<ll,ll> p,ll len){
    ll dx=(p.second*len%mod-p.first*p.first%mod+mod)%mod;
    return (dx*get_mul_inverse((len*len)%mod)%mod+mod)%mod;
}

void show_tree(int n){
    for(int i=1;i<=n*4;i++){
        cout<<tree[i].sum<<" "<<tree[i].sum_sq<<" | ";
    }
    cout<<endl;
}

int main(){
    std::ios::sync_with_stdio(false);
    ll n,q;
    cin>>n>>q;
    for(ll i=1;i<=n;i++){
        cin>>nums[i];
    }
    build_tree(1,n,1);
    for(ll i=0;i<q;++i){
        ll op;
        cin>>op;
        if(op==1){
            ll t,d;
            cin>>t>>d;
            update_add(t,d,1);
        }
        else{
            ll l,r;
            cin>>l>>r;
            cout<<get_ans(get_sum(l,r,1),(r-l+1))<<endl;
        }
    }
}
2024/12/5 19:26
加载中...