#include <bits/stdc++.h>
using namespace std;
int n, val[200005], pos[200005];
vector<int> a[200005];
int tin[200005], ver[2 * 200005], tout[200005], tt, h[200005],
    lca[20][2 * 200005];
void preDFS(int u, int pa) {
  tin[u] = tout[u] = ++tt;
  ver[tt] = u;
  for (auto v : a[u]) {
    if (v == pa) continue;
    h[v] = h[u] + 1;
    preDFS(v, u);
    tout[u] = ++tt;
    ver[tt] = u;
  }
}
void prepareLCA() {
  for (int i = 1; i <= tt; i++) lca[0][i] = ver[i];
  for (int j = 1; (1 << j) <= tt; j++)
    for (int i = 1; i + (1 << j) - 1 <= tt; i++)
      if (h[lca[j - 1][i]] < h[lca[j - 1][i + (1 << (j - 1))]])
        lca[j][i] = lca[j - 1][i];
      else
        lca[j][i] = lca[j - 1][i + (1 << (j - 1))];
}
bool isAnc(int u, int v) { return tin[u] <= tin[v] && tout[u] >= tout[v]; }
int LCA(int u, int v) {
  if (tin[u] > tin[v]) swap(u, v);
  if (isAnc(u, v)) return u;
  if (isAnc(v, u)) return v;
  int L = tout[u];
  int R = tin[v];
  int k = log2(R - L + 1);
  int uL = lca[k][L];
  int uR = lca[k][R - (1 << k) + 1];
  if (h[uL] < h[uR]) return uL;
  return uR;
}
int dist(int u, int v) {
  int w = LCA(u, v);
  return h[u] + h[v] - 2 * h[w];
}
struct ITNode {
  int u, v;
  ITNode(int _u = 0, int _v = 0) : u(_u), v(_v) {}
  ITNode check(int w) {
    int x = dist(u, v);
    int y = dist(u, w);
    int z = dist(v, w);
    if (x + y == z) return ITNode(v, w);
    if (y + z == x) return ITNode(u, v);
    if (x + z == y) return ITNode(u, w);
    return ITNode(-1, -1);
  }
};
struct IntervalTree {
  ITNode t[200005 << 2];
  ITNode Merge(ITNode p, ITNode q) {
    if (p.u == -1 || q.u == -1) return ITNode(-1, -1);
    if (!p.u && !p.v) return q;
    if (!q.u && !q.v) return p;
    p = p.check(q.u);
    p = p.check(q.v);
    return p;
  }
  void update(int l, int r, int id, int x) {
    if (l == r) {
      t[id] = ITNode(pos[l], pos[l]);
      return;
    }
    if (x <= (r + l) / 2)
      update(l, (r + l) / 2, id * 2, x);
    else
      update((r + l) / 2 + 1, r, id * 2 + 1, x);
    t[id] = Merge(t[id * 2], t[id * 2 + 1]);
  }
  ITNode get(int l, int r, int id, int x, int y) {
    if (l > y || r < x) return ITNode(0, 0);
    if (l >= x && r <= y) return t[id];
    auto a = get(l, (r + l) / 2, id * 2, x, y);
    auto b = get((r + l) / 2 + 1, r, id * 2 + 1, x, y);
    return Merge(a, b);
  }
} t;
void inline getInt(int &x) {
  char ch = getchar();
  x = 0;
  while (ch < '0' || ch > '9') ch = getchar();
  while (ch >= '0' && ch <= '9')
    x = (x << 3) + (x << 1) + ch - '0', ch = getchar();
}
int main() {
  ios_base::sync_with_stdio(0);
  cin.tie(0);
  cout.tie(0);
  getInt(n);
  for (int i = 1; i <= n; i++) {
    getInt(val[i]);
    pos[val[i]] = i;
  }
  for (int v = 2; v <= n; v++) {
    int u;
    getInt(u);
    a[u].push_back(v);
  }
  preDFS(1, -1);
  prepareLCA();
  for (int i = 0; i <= n - 1; i++) t.update(0, n - 1, 1, i);
  int numQ;
  getInt(numQ);
  while (numQ--) {
    int type, u, v;
    getInt(type);
    if (type == 2) {
      int l = 0, r = n + 1;
      while (r - l > 1) {
        auto z = t.get(0, n - 1, 1, 0, (r + l) / 2 - 1);
        if (z.u > 0 && z.v > 0)
          l = (r + l) / 2;
        else
          r = (r + l) / 2;
      }
      cout << l << '\n';
    } else {
      getInt(u);
      getInt(v);
      int p = val[u], q = val[v];
      swap(pos[p], pos[q]);
      swap(val[u], val[v]);
      t.update(0, n - 1, 1, p);
      t.update(0, n - 1, 1, q);
    }
  }
}
