Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include<bits/stdc++.h>
- using namespace std;
- #define nl "\n"
- #define fi first
- #define se second
- #define pb push_back
- #define ll long long
- #define RV return void
- #define sz(x) int(x.size())
- #define all(v) v.begin(), v.end()
- #define rall(v) v.rbegin(), v.rend()
- #define fixed(n) fixed << setprecision(n)
- #define cin(v) for(auto&x:v) cin >> x;
- #define cout(v) for(auto&x:v) cout << x << " ";
- void files(){
- #ifndef ONLINE_JUDGE
- freopen("input.txt", "r", stdin);
- freopen("output.txt", "w", stdout);
- #endif
- }
- const ll mod = 1e9+7;
- ll mul(ll a , ll b){
- return ( (a%mod) * (b % mod)) %mod;
- }
- struct node {
- ll sumx , sumx2 , sumx3 , ret , tot ;
- node(){
- sumx=sumx2=sumx3=ret=tot=0;
- }
- node(ll x){
- sumx = x;
- sumx2= mul(x,x);
- sumx3= mul(x, mul(x,x));
- tot = ret =0;
- }
- // void change(ll x){
- // val += x;
- // }
- };
- struct Lazy{
- vector < node > tree;
- vector<ll>lazy;
- int tree_size;
- Lazy(int n){
- tree_size = 1;
- while (tree_size < n) tree_size *= 2;
- tree.assign(2 * tree_size , node());
- lazy.assign(2 * tree_size , 0);
- }
- node merge(node a , node b){
- node res = node();
- res.sumx= a.sumx % mod + b.sumx %mod;
- res.sumx2= a.sumx2 % mod + b.sumx2 %mod;
- res.sumx3= a.sumx3 % mod + b.sumx3 %mod;
- res.ret= a.ret % mod + b.ret %mod;
- res.tot= a.tot % mod + b.tot %mod;
- res.sumx %=mod;
- res.sumx2 %=mod;
- res.sumx3 %=mod;
- res.tot %=mod;
- res.ret %=mod;
- return res;
- }
- void build(vector < ll > &v , int x , int lx , int rx){
- if(rx - lx == 1){
- if(lx < sz(v)) tree[x] = node(v[lx]);
- return;
- }
- int m = (lx + rx) / 2;
- build(v , 2 * x + 1 , lx , m);
- build(v , 2 * x + 2 , m , rx);
- tree[x] = merge(tree[2 * x + 1] , tree[2 * x + 2]);
- }
- void build(vector < ll > &v){
- build(v , 0 , 0 , tree_size);
- }
- void push(int x , int lx , int rx){
- if(lazy[x]>0 ){
- // cout << x << " " << lazy[x] << nl;
- tree[x].tot += lazy[x];
- tree[x].tot %= mod;
- if(rx - lx != 1){
- lazy[2 * x + 1] += lazy[x];
- lazy[2 * x + 1] %= mod;
- lazy[2 * x + 2] += lazy[x];
- lazy[2 * x + 2] %= mod;
- }
- lazy[x] = 0;
- }
- }
- void update(int l , int r , int val , int x , int lx , int rx){
- push(x , lx , rx);
- if(lx >= r || rx <= l) return;
- if(lx >= l && rx <= r){
- tree[x].tot += val;
- tree[x].tot %= mod;
- // cout << x << " " << tree[x].tot << nl;
- if(rx - lx != 1){
- lazy[x * 2 + 1] += val;
- lazy[x * 2 + 1] %= mod;
- lazy[x * 2 + 2] += val;
- lazy[x * 2 + 2] %= mod;
- }
- return;
- }
- int m = (lx + rx) / 2;
- update(l , r , val , 2 * x + 1 , lx , m);
- update(l , r , val , 2 * x + 2 , m , rx);
- tree[x] = merge(tree[2 * x + 1] , tree[2 * x + 2]);
- }
- void update(int l , int r , int val){
- update(l , r , val , 0 , 0 , tree_size);
- }
- node query(int l , int r , int x , int lx , int rx){
- // cout << x << " " << tree[x].tot << " " << lazy[x] << nl;
- push(x , lx , rx);
- if(lx >= r || rx <= l) return node();
- if(lx >= l && rx <= r) {
- // y^3 + sum(x^3) + 3yx^2 + 3xy^2
- // cout << x << nl;
- // cout << tree[x].tot << nl;
- ll y = tree[x].tot %mod;
- tree[x].ret = mul(mul(y , mul(y,y)) , rx-lx);
- tree[x].ret %= mod;
- tree[x].ret += tree[x].sumx3;
- tree[x].ret %= mod;
- tree[x].ret += mul( mul(3,y) , tree[x].sumx2);
- tree[x].ret %= mod;
- tree[x].ret += mul(mul(3 , mul(y,y)) , tree[x].sumx);
- tree[x].ret %= mod;
- return tree[x];
- }
- int m = (lx + rx) / 2;
- node left = query(l , r , 2 * x + 1 , lx , m);
- node right = query(l , r , 2 * x + 2 , m , rx);
- node ans=node();
- ans.ret = left.ret%mod + right.ret%mod;
- ans.ret %= mod;
- return ans;
- }
- node query(int l , int r) {
- return query(l, r, 0, 0, tree_size);
- }
- };
- void solve(){
- int n ; cin >> n ;
- vector < ll > v(n);
- cin(v);
- Lazy seg(n);
- seg.build(v);
- int q; cin >> q;
- ll y =0;
- while(q--){
- int op ;
- cin >> op;
- if(op==1){
- // update
- int l , r ;
- ll val; cin >> l >> r >> val;
- seg.update(l-1 ,r , val);
- }else{
- int l ,r; cin >> l >> r;
- cout << seg.query(l-1 ,r).ret<< nl;
- }
- }
- }
- // 955575183
- // 270524667
- // 624270388
- // 811103748
- // 469845835
- // 1358
- // 1792
- // 3710
- int main(){
- ios_base::sync_with_stdio(false);
- cin.tie(nullptr);
- cout.tie(nullptr);
- // files();
- int testCase=1;
- // cin >> testCase ;
- for(int i=1 ; i <= testCase ; i++){
- // cout << "Case "<< i <<": " << nl;
- solve();
- }
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement