#include <bits/stdc++.h>
#define int long long
using namespace std;
constexpr int MAXN = 5e5 + 5,inf = 1e18;
int n,m,opt,l,r,x,a[MAXN];
struct Rukkhadevata
{
int max,min,smx,smn,mxCnt,mnCnt,sum;
int lazmx,lazmn,lazsm;
}tree[MAXN << 2];
inline void pushup(int rt)
{
tree[rt].sum = tree[rt << 1].sum + tree[rt << 1 | 1].sum;
if(tree[rt << 1].max == tree[rt << 1 | 1].max)
{
tree[rt].max = tree[rt << 1].max;
tree[rt].smx = max(tree[rt << 1].smx,tree[rt << 1 | 1].smx);
tree[rt].mxCnt = tree[rt << 1].mxCnt + tree[rt << 1 | 1].mxCnt;
}
else if(tree[rt << 1].max > tree[rt << 1 | 1].max)
{
tree[rt].max = tree[rt << 1].max;
tree[rt].smx = max(tree[rt << 1].smx,tree[rt << 1 | 1].max);
tree[rt].mxCnt = tree[rt << 1].mxCnt;
}
else
{
tree[rt].max = tree[rt << 1 | 1].max;
tree[rt].smx = max(tree[rt << 1].max,tree[rt << 1 | 1].smx);
tree[rt].mxCnt = tree[rt << 1 | 1].mxCnt;
}
if(tree[rt << 1].min == tree[rt << 1 | 1].min)
{
tree[rt].min = tree[rt << 1].min;
tree[rt].smn = min(tree[rt << 1].smn,tree[rt << 1 | 1].smn);
tree[rt].mnCnt = tree[rt << 1].mnCnt + tree[rt << 1 | 1].mnCnt;
}
else if(tree[rt << 1].min < tree[rt << 1 | 1].min)
{
tree[rt].min = tree[rt << 1].min;
tree[rt].smn = min(tree[rt << 1].smn,tree[rt << 1 | 1].min);
tree[rt].mnCnt = tree[rt << 1].mnCnt;
}
else
{
tree[rt].min = tree[rt << 1 | 1].min;
tree[rt].smn = min(tree[rt << 1].min,tree[rt << 1 | 1].smn);
tree[rt].mnCnt = tree[rt << 1 | 1].mnCnt;
}
}
inline void build(int l,int r,int rt)
{
tree[rt].lazmn = inf,tree[rt].lazmx = -inf;
if(l == r)
{
tree[rt].sum = tree[rt].max = tree[rt].min = a[l];
tree[rt].smx = -inf,tree[rt].smn = inf;
tree[rt].mxCnt = tree[rt].mnCnt = 1;
return ;
}
int mid = (l + r) >> 1;
build(l,mid,rt << 1);
build(mid + 1,r,rt << 1 | 1);
pushup(rt);
}
inline void updateSum(int rt,int val,int l,int r)
{
tree[rt].sum += (r - l + 1) * val;
tree[rt].max += val,tree[rt].min += val;
if(tree[rt].lazmn != inf)
tree[rt].lazmn += val;
if(tree[rt].lazmx != -inf)
tree[rt].lazmx += val;
if(tree[rt].smn != inf)
tree[rt].smn += val;
if(tree[rt].smx != -inf)
tree[rt].smx += val;
tree[rt].lazsm += val;
}
inline void updateMin(int rt,int val)
{
if(tree[rt].max <= val)
return ;
tree[rt].sum += (val - tree[rt].max) * tree[rt].mxCnt;
if(tree[rt].smn == tree[rt].max)
tree[rt].smn = val;
if(tree[rt].min == tree[rt].max)
tree[rt].min = val;
tree[rt].lazmx = min(tree[rt].lazmx,val),tree[rt].max = val,tree[rt].lazmn = val;
}
inline void updateMax(int rt,int val)
{
if(tree[rt].min > val)
return ;
tree[rt].sum += (val - tree[rt].min) * tree[rt].mnCnt;
if(tree[rt].smx == tree[rt].min)
tree[rt].smx = val;
if(tree[rt].max == tree[rt].min)
tree[rt].max = val;
tree[rt].lazmn = max(tree[rt].lazmn,val),tree[rt].min = val,tree[rt].lazmx = val;
}
inline void pushdown(int rt,int l,int r)
{
int mid = (l + r) >> 1;
if(tree[rt].lazsm)
{
updateSum(rt << 1,tree[rt].lazsm,l,mid);
updateSum(rt << 1 | 1,tree[rt].lazsm,mid + 1,r);
tree[rt].lazsm = 0;
}
if(tree[rt].lazmx != -inf)
{
updateMax(rt << 1,tree[rt].lazmx);
updateMax(rt << 1 | 1,tree[rt].lazmx);
tree[rt].lazmx = -inf;
}
if(tree[rt].lazmn != inf)
{
updateMin(rt << 1,tree[rt].lazmn);
updateMin(rt << 1 | 1,tree[rt].lazmn);
tree[rt].lazmn = inf;
}
}
inline void modifySum(int rt,int l,int r,int L,int R,int val)
{
if(L <= l && R >= r)
return updateSum(rt,val,l,r);
pushdown(rt,l,r);
int mid = (l + r) >> 1;
if(L <= mid)
modifySum(rt << 1,l,mid,L,R,val);
if(R > mid)
modifySum(rt << 1 | 1,mid + 1,r,L,R,val);
pushup(rt);
}
inline void modifyMin(int rt,int l,int r,int L,int R,int val)
{
if(tree[rt].max <= val)
return ;
if(L <= l && r >= r && tree[rt].smx < val)
return updateMin(rt,val);
pushdown(rt,l,r);
int mid = (l + r) >> 1;
if(L <= mid)
modifyMin(rt << 1,l,mid,L,R,val);
if(R > mid)
modifyMin(rt << 1 | 1,mid + 1,r,L,R,val);
pushup(rt);
}
inline void modifyMax(int rt,int l,int r,int L,int R,int val)
{
if(tree[rt].min >= val)
return ;
if(L <= l && R >= r && tree[rt].smn > val)
return updateMax(rt,val);
int mid = (l + r) >> 1;
if(L <= mid)
modifyMax(rt << 1,l,mid,L,R,val);
if(R > mid)
modifyMax(rt << 1 | 1,mid + 1,r,L,R,val);
pushup(rt);
}
inline int querySum(int rt,int l,int r,int L,int R)
{
if(L <= l && R >= r)
return tree[rt].sum;
pushdown(rt,l,r);
int mid = (l + r) >> 1,res = 0;
if(L <= mid)
res += querySum(rt << 1,l,mid,L,R);
if(R > mid)
res += querySum(rt << 1 | 1,mid + 1,r,L,R);
return res;
}
inline int queryMax(int rt,int l,int r,int L,int R)
{
if(L <= l && R >= r)
return tree[rt].max;
pushdown(rt,l,r);
int mid = (l + r) >> 1,res = -inf;
if(L <= mid)
res = max(res,queryMax(rt << 1,l,mid,L,R));
if(R > mid)
res= max(res,queryMax(rt << 1 | 1,mid + 1,r,L,R));
return res;
}
inline int queryMin(int rt,int l,int r,int L,int R)
{
if(L <= l && R >= r)
return tree[rt].min;
pushdown(rt,l,r);
int mid = (l + r) >> 1,res = inf;
if(L <= mid)
res = min(res,queryMin(rt << 1,l,mid,L,R));
if(R > mid)
res = min(res,queryMin(rt << 1 | 1,mid + 1,r,L,R));
return res;
}
signed main()
{
ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
cin >> n;
for(int i = 1;i <= n;i++)
cin >> a[i];
build(1,n,1);
cin >> m;
while(m--)
{
cin >> opt >> l >> r;
if(opt == 1)
{
cin >> x;
modifySum(1,1,n,l,r,x);
}
if(opt == 2)
{
cin >> x;
modifyMax(1,1,n,l,r,x);
}
if(opt == 3)
{
cin >> x;
modifyMin(1,1,n,l,r,x);
}
if(opt == 4)
cout << querySum(1,1,n,l,r) << '\n';
if(opt == 5)
cout << queryMax(1,1,n,l,r) << '\n';
if(opt == 6)
cout << queryMin(1,1,n,l,r) << '\n';
}
}