1 条题解
-
0
和上一题差不多,开两倍数组,用 维护队列区间,再用线段树完成修改即可。
代码:
#include<bits/stdc++.h> #define ls(p) p<<1 #define rs(p) p<<1|1 using namespace std; const int mod=998244353; struct f{ long long a,b; f operator *(const f &ano)const{ return {a*ano.a%mod,(a*ano.b%mod+b)%mod}; } }; f tr[8000005]; void up(int root){ tr[root]=tr[rs(root)]*tr[ls(root)]; } void build(int root,int l,int r){ tr[root]={1,0}; if(l==r){ return; } int mid=(l+r)>>1; build(ls(root),l,mid); build(rs(root),mid+1,r); } void change(int root,int l,int r,int x,f y){ if(l==r){ tr[root]=y; return; } int mid=(l+r)>>1; if(x<=mid){ change(ls(root),l,mid,x,y); } else{ change(rs(root),mid+1,r,x,y); } up(root); } f query(int root,int l,int r,int x,int y){ if(x<=l && r<=y){ return tr[root]; } int mid=(l+r)>>1; f ans={1,0}; if(y>mid){ ans=query(rs(root),mid+1,r,x,y); } if(x<=mid){ ans=ans*query(ls(root),l,mid,x,y); } return ans; } int l,r; int main(){ int q; cin>>q; build(1,1,1000002); l=q+1; r=q; while(q--){ int op; cin>>op; if(op==0){ f y; cin>>y.a>>y.b; change(1,1,1000002,--l,y); } else if(op==1){ f y; cin>>y.a>>y.b; change(1,1,1000002,++r,y); } else if(op==2){ change(1,1,1000002,l++,{1,0}); } else if(op==3){ change(1,1,1000002,r--,{1,0}); } else{ long long x; cin>>x; if(l>r){ cout<<x<<"\n"; continue; } f ans=query(1,1,1000002,l,r); cout<<(x*ans.a%mod+ans.b)%mod<<"\n"; } } return 0; }
- 1
信息
- ID
- 8143
- 时间
- 500ms
- 内存
- 1024MiB
- 难度
- 9
- 标签
- 递交数
- 11
- 已通过
- 3
- 上传者