分成三类
不受影响的城市以及城市的学校
受影响的城市里不受影响的学校
受影响的学校
第一类可以直接分别阵营和派系后乘起来
第二类可以和第一类一起派系但不考虑阵营
第三类暴力即可
#include<bits/stdc++.h>
using namespace std;
const int RLEN=1<<20|1;
inline char gc(){
static char ibuf[RLEN],*ib,*ob;
(ob==ib)&&(ob=(ib=ibuf)+fread(ibuf,1,RLEN,stdin));
return (ob==ib)?EOF:*ib++;
}
#define gc getchar
inline int read(){
char ch=gc();
int res=0,f=1;
while(!isdigit(ch))f^=ch=='-',ch=gc();
while(isdigit(ch))res=(res+(res<<2)<<1)+(ch^48),ch=gc();
return f?res:-res;
}
#define ll long long
#define re register
#define pii pair<int,int>
#define fi first
#define se second
#define pb push_back
#define cs const
#define bg begin
#define poly vector<int>
cs int mod=998244353;
inline int add(int a,int b){return (a+=b)>=mod?a-mod:a;}
inline void Add(int &a,int b){(a+=b)>=mod?a-=mod:0;}
inline int dec(int a,int b){return (a-=b)<0?a+mod:a;}
inline void Dec(int &a,int b){(a-=b)<0?a+=mod:0;}
inline int mul(int a,int b){return 1ll*a*b%mod;}
inline void Mul(int &a,int b){a=1ll*a*b%mod;}
inline int ksm(int a,int b,int res=1){for(;b;b>>=1,Mul(a,a))(b&1)&&(Mul(res,a),1);return res;}
inline int Inv(int x){return ksm(x,mod-2);}
inline void chemx(int &a,int b){a<b?a=b:0;}
inline void chemn(int &a,int b){a>b?a=b:0;}
cs int N=1005,M=2505;
int n,c,c0,c1,d0,d1,K;
int bel[N],val[N],s[N],sum[N],req[N],ban[N],vis[N];
vector<int> lim[N],city,sco;
int f[M],g[M],p[M][M],tp1[M][M],tp2[M][M];
inline void calc_p(){
int tot1=0,tot2=0,r1=0,r2=0;
p[0][0]=1;
for(int o=1;o<=c;o++){
if(!lim[o].size())continue;
for(int i=min(tot1,c0);~i;i--)
for(int j=min(tot2,d0);~j;j--)
tp1[i][j]=tp2[i][j]=p[i][j];
for(int &x:lim[o]){
tot2+=val[x];
int t0=ban[x]!=0,t1=ban[x]!=1,t2=ban[x]!=2,t3=ban[x]!=3;
for(int i=min(tot1,c0);~i;i--)
for(int j=min(tot2,d0);~j;j--)
if(j>=val[x]){
tp1[i][j]=add(tp1[i][j]*t1,tp1[i][j-val[x]]*t0);
tp2[i][j]=add(tp2[i][j]*t3,tp2[i][j-val[x]]*t2);
chemx(r1,i),chemx(r2,j);
}
else tp1[i][j]=tp1[i][j]*t1,tp2[i][j]=tp2[i][j]*t3,chemx(r1,i),chemx(r2,j);;
}
tot1+=sum[o];
for(int i=min(tot1,c0);~i;i--)
for(int j=min(tot2,d0);~j;j--)
if(i>=sum[o])p[i][j]=add(tp1[i-sum[o]][j],tp2[i][j]),chemx(r1,i),chemx(r2,j);
else p[i][j]=tp2[i][j],chemx(r1,i),chemx(r2,j);;
}
for(int i=min(tot1,c0);~i;i--)
memset(tp1[i],0,sizeof(int)*(min(tot2,d0)+1)),memset(tp2[i],0,sizeof(int)*(min(tot2,d0)+1));
}
inline void calc_f(){
memset(f,0,sizeof(int)*(c0+1));
f[0]=1;int tot=0,res;
for(int &x:city){
tot+=x;
for(int j=min(c0,tot);~j;j--){
res=0;
if(j>=x)Add(res,f[j-x]);
if(tot-j<=c1)Add(res,f[j]);
f[j]=res;
}
}
}
inline void calc_g(){
memset(g,0,sizeof(int)*(d0+1));
g[0]=1;int tot=0,res;
for(int &x:sco){
tot+=x;
for(int j=min(d0,tot);~j;j--){
res=0;
if(j>=x)Add(res,g[j-x]);
if(tot-j<=d1)Add(res,g[j]);
g[j]=res;
}
}
}
inline void solve(){
n=read(),c=read();int tot=0;
c0=read(),c1=read(),d0=read(),d1=read();
for(int i=1;i<=n;i++)
bel[i]=read(),val[i]=read(),tot+=val[i],sum[bel[i]]+=val[i];
K=read();
for(int i=1;i<=K;i++){
int pos=read(),r=read();
req[bel[pos]]=1,ban[pos]=r,vis[pos]=1;
lim[bel[pos]].pb(pos);
}
for(int i=1;i<=n;i++)if(!vis[i])s[bel[i]]+=val[i],sco.pb(val[i]);
for(int i=1;i<=c;i++)if(!req[i]&&s[i])city.pb(s[i]);
calc_f();
calc_g();
calc_p();
int res=0;
for(int i=1;i<=c0;i++)Add(f[i],f[i-1]);
for(int i=1;i<=d0;i++)Add(g[i],g[i-1]);
for(int i=0;i<=c0;i++)
for(int j=0;j<=d0;j++){
int tmp=1;
if(c0-i>=tot-c1-i)Mul(tmp,dec(f[c0-i],tot-c1-i-1>=0?f[tot-c1-i-1]:0));
if(d0-j>=tot-d1-j)Mul(tmp,dec(g[d0-j],tot-d1-j-1>=0?g[tot-d1-j-1]:0));
Add(res,mul(tmp,p[i][j]));
}
cout<<res<<'
';
memset(p,0,sizeof(p));
for(int i=1;i<=n;i++)vis[i]=val[i]=bel[i]=ban[i]=0;
for(int i=1;i<=c;i++)sum[i]=s[i]=req[i]=0,lim[i].clear();
sco.clear(),city.clear();
}
int main(){
int T=read();
while(T--)solve();
}