#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <cstdlib>
#include <cstdint>
#include <random>
#include <functional>
#include <vector>
#include <queue>
#include <stack>
#include <bitset>
#include <unordered_set>
#include <unordered_map>
#include <set>
#include <map>
typedef long long LL;
typedef unsigned long long ull;
typedef std::pair<int,int> PII;
typedef std::pair<LL,LL> PLL;
#define rep(i,l,r) for(int i(l);i<=r;++i)
#define per(i,r,l) for(int i(r);i>=l;--i)
template<typename T>T min(T a,T b){return a<b?a:b;}
template<typename T>T max(T a,T b){return a>b?a:b;}
const auto N = 100010;
const auto M = 200010;
const auto mod = 0;
const auto INF = 0x3f3f3f3f;
int n,m,q;
int a[N],b[N];
int to[N];
int c,T;
int dfn[N],low[N];
int scc[N],sc,dn;
int s[N],tp;
int num,root[N];
int in[N],ans;
std::bitset<N> vis;
std::vector<int> e[N],g[N];
struct node{int x,ls,rs;}t[1<<27];
void update(int p1,int p2,int l,int r,int x,int d){
if(l==r){t[p2].x=d;return ;}
int mid=(l+r)>>1;
if(x<=mid){t[p2].ls=++num;t[p2].rs=t[p1].rs;update(t[p1].ls,t[p2].ls,l,mid,x,d);}
else{t[p2].rs=++num;t[p2].ls=t[p1].ls;update(t[p1].rs,t[p2].rs,mid+1,r,x,d);}
t[p2].x=max(t[t[p2].ls].x,t[t[p2].rs].x);
}
void update(int p,int l,int r,int x,int d){
if(l==r){t[p].x=d;return ;}
int mid=(l+r)>>1;
if(x<=mid){update(t[p].ls,l,mid,x,d);}
else{update(t[p].rs,mid+1,r,x,d);}
t[p].x=max(t[t[p].ls].x,t[t[p].rs].x);
}
void merge(int p1,int p2){
t[p1].x=max(t[p1].x,t[p2].x);
if(t[p1].ls!=t[p2].ls){merge(t[p1].ls,t[p2].ls);}
else{t[p1].ls=(t[p1].ls|t[p2].ls);}
if(t[p1].rs!=t[p2].rs){merge(t[p1].rs,t[p2].rs);}
else{t[p1].rs=(t[p1].rs|t[p2].rs);}
}
void tarjan(int u){
s[++tp]=u;vis[u]=1;
dfn[u]=low[u]=++dn;
for(int v : e[u]){
if(!dfn[v]){tarjan(v);low[u]=min(low[u],low[v]);}
else if(vis[v]){low[u]=min(low[u],dfn[v]);}
}
if(low[u]!=dfn[u]){return ;}
int v;
++sc;
root[sc]=++num;
do{
v=s[tp];--tp;
vis[v]=0;
scc[v]=sc;
update(0,root[sc],1,n,a[v],b[v]);
}while(u!=v);
}
void dfs(int u){
vis[u]=1;
for(int v : g[u]){
if(vis[v]){continue;}
dfs(v);
merge(root[u],root[v]);
}
}
int query(int p,int pl,int pr,int l,int r){
if(pl>=l && pr<=r){return t[p].x;}
int mid=(pl+pr)>>1;
int res=0;
if(l<=mid){res=max(res,query(t[p].ls,pl,mid,l,r));}
if(r>mid){res=max(res,query(t[p].rs,mid+1,pr,l,r));}
return res;
}
void dfs(int u,int x,int y){
if(a[u]>=x && a[u]<=y){ans=max(ans,b[u]);}
vis[u]=1;
for(int v : e[u]){
if(vis[v]){continue;}
dfs(v,x,y);
}
}
int main(){
freopen("recall.in","r",stdin);
freopen("recall.out","w",stdout);
scanf("%d%d",&c,&T);
while(T--){
scanf("%d%d%d",&n,&m,&q);
rep(i,1,n){e[i].clear();g[i].clear();}
memset(dfn,0,sizeof dfn);
memset(scc,0,sizeof scc);
memset(low,0,sizeof low);
memset(in,0,sizeof in);
vis&=0;tp=dn=sc=num=0;
while(m--){int u,v;scanf("%d%d",&u,&v);e[u].emplace_back(v);}
rep(i,1,n){scanf("%d",&a[i]);}
rep(i,1,n){scanf("%d",&b[i]);}
rep(i,1,n){if(!dfn[i]){tarjan(i);}}
rep(u,1,n){
for(int v : e[u]){
if(scc[u]==scc[v]){continue;}
g[scc[u]].emplace_back(scc[v]);
++in[scc[v]];
}
}
rep(i,1,sc){if(!in[i]){dfs(i);}}
while(q--){
int op,k,x,y;
scanf("%d",&op);
if(op==3){
scanf("%d%d%d",&k,&x,&y);
if(c==6){printf("%d\n",query(root[scc[k]],1,n,x,y));}
else{
ans=0;vis&=0;dfs(k,x,y);
printf("%d\n",ans);
}
}
else{
scanf("%d%d",&x,&y);
if(op==1){std::swap(a[x],a[y]);}
else{std::swap(b[x],b[y]);}
}
}
}
return 0;
}