#include <bits/stdc++.h>
const int MAXN = 200007;
struct Edge {
  int to, nextEdge;
} e[MAXN << 1];
int cntEdge, head[MAXN];
inline void addEdge(int u, int v) {
  ++cntEdge;
  e[cntEdge].to = v, e[cntEdge].nextEdge = head[u], head[u] = cntEdge;
  return;
}
int idx[MAXN], p[MAXN];
int depth[MAXN], dfn[MAXN], low[MAXN], wson[MAXN], fa[MAXN], time_stamp,
    size[MAXN], top[MAXN];
void dfs1(int u) {
  size[u] = 1;
  for (int it = head[u]; it != 0; it = e[it].nextEdge) {
    int v = e[it].to;
    if (v == fa[u]) continue;
    fa[v] = u;
    depth[v] = depth[u] + 1;
    dfs1(v);
    size[u] += size[v];
    if (size[v] > size[wson[u]]) wson[u] = v;
  }
  return;
}
void dfs2(int u) {
  dfn[u] = ++time_stamp;
  if (!top[u]) top[u] = u;
  if (wson[u]) {
    top[wson[u]] = top[u];
    dfs2(wson[u]);
  }
  for (int it = head[u]; it != 0; it = e[it].nextEdge) {
    int v = e[it].to;
    if (v == fa[u] || v == wson[u]) continue;
    dfs2(v);
  }
  low[u] = time_stamp;
  return;
}
inline void split() {
  depth[1] = 1;
  dfs1(1);
  dfs2(1);
  return;
}
inline int getLCA(int x, int y) {
  while (top[x] != top[y]) {
    if (depth[top[x]] < depth[top[y]]) std::swap(x, y);
    x = fa[top[x]];
  }
  return depth[x] < depth[y] ? x : y;
}
struct SegmentTree {
  struct Node {
    std::pair<int, int> ep;
    int lc, rc;
  } node[MAXN << 1];
  int cntNode, root;
  inline std::pair<int, int> merge(const std::pair<int, int> &l,
                                   const std::pair<int, int> &r) {
    int tmp[4];
    tmp[0] = l.first, tmp[1] = l.second;
    tmp[2] = r.first, tmp[3] = r.second;
    if (tmp[0] == -1 || tmp[2] == -1) {
      return std::pair<int, int>(-1, -1);
    } else {
      for (int a = 0; a < 4; ++a) {
        int i = tmp[a];
        for (int b = a + 1; b < 4; ++b) {
          int j = tmp[b];
          int lca = getLCA(i, j);
          for (int c = 0; c < 4; ++c) {
            if (c == a || c == b) continue;
            int u = tmp[c];
            if ((dfn[lca] <= dfn[u] && low[u] <= low[lca]) &&
                ((dfn[u] <= dfn[i] && low[i] <= low[u]) ||
                 (dfn[u] <= dfn[j] && low[j] <= low[u]))) {
              for (int d = c + 1; d < 4; ++d) {
                if (d == a || d == b) continue;
                int v = tmp[d];
                if ((dfn[lca] <= dfn[v] && low[v] <= low[lca]) &&
                    ((dfn[v] <= dfn[i] && low[i] <= low[v]) ||
                     (dfn[v] <= dfn[j] && low[j] <= low[v]))) {
                  return std::pair<int, int>(i, j);
                }
              }
            }
          }
        }
      }
    }
    return std::pair<int, int>(-1, -1);
  }
  void build(int &cur, const int &l, const int &r) {
    cur = ++cntNode;
    if (l == r) {
      node[cur].ep = std::pair<int, int>(idx[l], idx[l]);
      return;
    }
    const int &mid = (l + r) >> 1;
    build(node[cur].lc, l, mid);
    build(node[cur].rc, mid + 1, r);
    node[cur].ep = merge(node[node[cur].lc].ep, node[node[cur].rc].ep);
    return;
  }
  void modify(const int &cur, const int &l, const int &r, const int &aim) {
    if (l == r) {
      node[cur].ep = std::pair<int, int>(idx[l], idx[l]);
      return;
    }
    const int &mid = (l + r) >> 1;
    if (aim <= mid)
      modify(node[cur].lc, l, mid, aim);
    else
      modify(node[cur].rc, mid + 1, r, aim);
    node[cur].ep = merge(node[node[cur].lc].ep, node[node[cur].rc].ep);
    return;
  }
  int query(const int &cur, const int &l, const int &r,
            std::pair<int, int> pre) {
    if (l == r) return l;
    std::pair<int, int> tmp = merge(pre, node[node[cur].lc].ep);
    const int &mid = (l + r) >> 1;
    if (tmp.first != -1)
      return query(node[cur].rc, mid + 1, r, tmp);
    else
      return query(node[cur].lc, l, mid, pre);
  }
} tree;
int main() {
  int n;
  scanf("%d", &n);
  for (int i = 1; i <= n; ++i) {
    int tmp;
    scanf("%d", &tmp);
    idx[tmp] = i;
    p[i] = tmp;
  }
  for (int i = 2; i <= n; ++i) {
    int tmp;
    scanf("%d", &tmp);
    addEdge(i, tmp);
    addEdge(tmp, i);
  }
  split();
  idx[n] = -1;
  tree.build(tree.root, 0, n);
  int q;
  scanf("%d", &q);
  while (q--) {
    int type;
    scanf("%d", &type);
    if (type == 1) {
      int i, j;
      scanf("%d%d", &i, &j);
      std::swap(p[i], p[j]);
      idx[p[i]] = i, idx[p[j]] = j;
      tree.modify(tree.root, 0, n, p[i]);
      tree.modify(tree.root, 0, n, p[j]);
    } else
      printf("%d\n",
             tree.query(tree.root, 0, n, std::pair<int, int>(idx[0], idx[0])));
  }
  return 0;
}
