1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121
| #include"bits/stdc++.h" #define re register #define int unsigned long long #define ls(p) tr[p].ls #define rs(p) tr[p].rs #define pii pair<int,int> #define fi first #define se second using namespace std; const int maxn=2.5e5+10,maxm=9; int n,m,rt,segcnt; int A[maxn],B[maxn],ans[maxn]; vector<pii> q[maxn]; struct Stack{ int top; int stk[maxn]; }a,b; struct matrix{ int a[maxm]; inline matrix operator * (const matrix &val)const{ return{ a[0]+val.a[0], a[1]+val.a[1], a[2]+val.a[2]+a[0]*val.a[4]+a[1]*val.a[5], a[3]+val.a[3]+a[0]*val.a[6]+a[1]*val.a[7]+a[2]*val.a[8], a[4]+val.a[4],a[5]+val.a[5], a[6]+val.a[6]+a[4]*val.a[8], a[7]+val.a[7]+a[5]*val.a[8], a[8]+val.a[8] }; } inline void clear(){memset(a,0,sizeof a);} }; matrix upd={0,0,0,0,0,0,0,0,1}; struct Data{ int a,b,ab,AB,len; inline void init(int A,int B){a=A,b=B,ab=A*B,AB=0,len=1;} inline Data operator * (const matrix &tag)const{ return{ a+len*tag.a[0], b+len*tag.a[1], ab+len*tag.a[2]+a*tag.a[4]+b*tag.a[5], AB+len*tag.a[3]+a*tag.a[6]+b*tag.a[7]+ab*tag.a[8], len }; } inline Data operator + (const Data &s)const{return {a+s.a,b+s.b,ab+s.ab,AB+s.AB,len+s.len};} }; struct tree{ int ls,rs; Data s; matrix tag; }tr[maxn<<1]; inline void up(int p){tr[p].s=tr[ls(p)].s+tr[rs(p)].s;} inline void add(int p,matrix val){tr[p].s=tr[p].s*val,tr[p].tag=tr[p].tag*val;} inline void down(int p){add(ls(p),tr[p].tag),add(rs(p),tr[p].tag),tr[p].tag.clear();} inline void build(int l,int r,int &p){ p=++segcnt; if(l==r){tr[p].s.init(A[l],B[l]);return;} int mid=(l+r)>>1; build(l,mid,ls(p)),build(mid+1,r,rs(p)); up(p); } inline void update(int l,int r,int L,int R,matrix val,int p){ if(l>=L&&r<=R){add(p,val);return;} int mid=(l+r)>>1;down(p); if(L<=mid) update(l,mid,L,R,val,ls(p)); if(R>mid) update(mid+1,r,L,R,val,rs(p)); up(p); } inline Data query(int l,int r,int L,int R,int p){ if(l>=L&&r<=R) return tr[p].s; int mid=(l+r)>>1;down(p); if(R<=mid) return query(l,mid,L,R,ls(p)); if(L>mid) return query(mid+1,r,L,R,rs(p)); return query(l,mid,L,R,ls(p))+query(mid+1,r,L,R,rs(p)); } signed main(){ #ifndef ONLINE_JUDGE freopen("1.in","r",stdin); freopen("1.out","w",stdout); #endif ios::sync_with_stdio(0),cin.tie(0),cout.tie(0); int _;cin>>_; cin>>n; for(re int i=1;i<=n;++i) cin>>A[i]; for(re int i=1;i<=n;++i) cin>>B[i]; build(1,n,rt); cin>>m; for(re int i=1,l,r;i<=m;++i){ cin>>l>>r; q[r].push_back({l,i}); } for(re int i=1;i<=n;++i){ while(a.top&&A[a.stk[a.top]]<A[i]){ matrix val={A[i]-A[a.stk[a.top]],0,0,0,0,A[i]-A[a.stk[a.top]],0,0,0}; update(1,n,a.stk[a.top-1]+1,a.stk[a.top],val,rt); --a.top; } a.stk[++a.top]=i; while(b.top&&B[b.stk[b.top]]<B[i]){ matrix val={0,B[i]-B[b.stk[b.top]],0,0,B[i]-B[b.stk[b.top]],0,0,0,0}; update(1,n,b.stk[b.top-1]+1,b.stk[b.top],val,rt); --b.top; } b.stk[++b.top]=i; update(1,n,1,i,upd,rt); for(auto x:q[i]) ans[x.se]=query(1,n,x.fi,i,rt).AB; } for(re int i=1;i<=m;++i) cout<<ans[i]<<'\n'; return 0; }
|