代码如下:
#include<bits/stdc++.h>
#define int long long
#define mod 998244353
#define N 200010
using namespace std;
int n,m,mark[N<<2],mins[N<<2],maxs[N<<2],a[N],q[N],ans;
void push_up(int rt){
maxs[rt]=max(maxs[rt<<1],maxs[rt<<1|1]);
mins[rt]=min(mins[rt<<1],mins[rt<<1|1]);
}
void push_down(int rt){
if(mark[rt]){
mark[rt<<1]+=mark[rt];
mark[rt<<1|1]+=mark[rt];
mins[rt<<1]+=mark[rt];
mins[rt<<1|1]+=mark[rt];
mark[rt]=0;
return;
}
}
void build(int l,int r,int rt){
if(l==r){
scanf("%lld",&maxs[rt]);
mark[rt]=mins[rt]=0;
return;
}
int mid=(l+r)>>1;
build(l,mid,rt<<1);
build(mid+1,r,rt<<1|1);
push_up(rt);
}
void update(int l,int r,int rt,int a,int b,int c){
if(maxs[rt]<=1) return;
if(a<=l&&b>=r&&(c==2||mins[rt])){
if(c==2){
mark[rt]++;
mins[rt]++;
}else{
mark[rt]--;
mins[rt]--;
}
return;
}
if(l==r&&c==1){
maxs[rt]=sqrt(maxs[rt]);
return;
}
push_down(rt);
int mid=(l+r)>>1;
if(a<=mid) update(l,mid,rt<<1,a,b,c);
if(b>mid) update(mid+1,r,rt<<1|1,a,b,c);
push_up(rt);
}
int qpow(int a,int b){
if(b==0) return 1;
int s=a;
while(--b) s=s*s%mod;
return s;
}
void query(int l,int r,int rt){
if(l==r){
a[l]=maxs[rt];
q[l]=mark[rt];
return;
}
push_down(rt);
int mid=(l+r)>>1;
query(l,mid,rt<<1);
query(mid+1,r,rt<<1|1);
}
signed main(){
scanf("%lld%lld",&n,&m);
build(1,n,1);
while(m--){
int op,l,r;
scanf("%lld%lld%lld",&op,&l,&r);
update(1,n,1,l,r,op);
}
query(1,n,1);
for(int i=1;i<=n;i++) ans=(ans+qpow(a[i],qpow(2,q[i])))%mod;
printf("%lld",ans);
return 0;
}