9 5 14
7 1 4 8 5 2 6 9 3
2 8
1 6
5 7
1 3
3 9
1 5
1 8
1 5
1 4
1 8
1 3
1 5
1 5
1 7
1 7
2 3
1 2
1 1
1 2
 6 5 8
1 2 6 3 4 5
2 4
1 3
1 6
3 5
2 5
1 1
1 4
1 1
2 1
2 5
2 2
2 3
1 4
 2 1 3
1 2
1 2
1 1
1 1
1 1

6
9
5
8
1
7
0
0
0
0
0
4
0
 6
5
4
3
 2
1
0

#include <bits/stdc++.h>
using namespace std;
template <typename T>
inline bool readn(T &x);
inline void rd();
inline void debug();
constexpr int N = 2e5 + 9;
constexpr int M = 450;
constexpr long long mod = 1e9 + 7;
int T, n, m, k, Q;
int val[N];
set<int> st[N], st2[N];
struct E {
  int x, y;
} e[N << 1];
int ind[N], up, id[N], is_big[N];
struct cmp1 {
  bool operator()(const pair<int, int> &a, const pair<int, int> &b) {
    return a.first < b.first;
  }
};
bool operator==(const pair<int, int> &a, const pair<int, int> &b) {
  return a.second == b.second;
}
struct Heap {
  priority_queue<pair<int, int>, vector<pair<int, int> >, cmp1> A, B;
  void insert(pair<int, int> x) { A.push(x); }
  void erase(pair<int, int> x) { B.push(x); }
  int top() {
    while (!B.empty() && A.top() == B.top()) A.pop(), B.pop();
    int p = A.top().second;
    A.pop();
    return p;
  }
  void pop() {
    while (!B.empty() && A.top() == B.top()) A.pop(), B.pop();
    A.pop();
  }
} heap[N];
int Query(int nowp) {
  int pos = nowp;
  if (is_big[nowp]) {
    pos = heap[id[nowp]].top();
  } else {
    int mx = val[nowp];
    for (auto x : st[nowp]) {
      if (val[x] > mx) {
        mx = val[x];
        pos = x;
      }
    }
  }
  for (auto x : st2[pos]) {
    heap[id[x]].erase({val[pos], pos});
  }
  return pos;
}
void change(int eid) {
  int x = e[eid].x, y = e[eid].y;
  st[x].erase(st[x].find(y));
  st[y].erase(st[y].find(x));
  if (is_big[x]) {
    st2[x].erase(st2[x].find(y));
    heap[id[x]].erase({val[y], y});
  }
  if (is_big[y]) {
    st2[y].erase(st2[y].find(x));
    heap[id[y]].erase({val[x], x});
  }
}
void Dmymax_ly() {
  rd();
  for (T = 1; T; T--) {
    readn(n);
    readn(m);
    readn(Q);
    up = sqrt(n) + 1;
    for (int i = 1; i <= n; ++i) readn(val[i]);
    for (int i = 1; i <= m; ++i) {
      int x, y;
      readn(x);
      readn(y);
      e[i] = {x, y};
      ++ind[x];
      ++ind[y];
    }
    for (int i = 1; i <= n; ++i) {
      if (ind[i] > up) {
        id[i] = ++id[0];
        is_big[i] = true;
        heap[id[0]].insert({val[i], i});
      }
    }
    for (int i = 1; i <= m; ++i) {
      int x = e[i].x, y = e[i].y;
      st[x].insert(y);
      st[y].insert(x);
      if (is_big[x]) {
        heap[id[x]].insert({val[y], y});
        st2[x].insert(y);
      }
      if (is_big[y]) {
        heap[id[y]].insert({val[x], x});
        st2[y].insert(x);
      }
    }
    for (int Case = 1; Case <= Q; ++Case) {
      int opt, pos;
      readn(opt);
      if (opt == 1) {
        readn(pos);
        pos = Query(pos);
        printf("%d\n", val[pos]);
        val[pos] = 0;
      } else {
        readn(pos);
        change(pos);
      }
    }
  }
  return;
}
int main() {
  Dmymax_ly();
  return 0;
}
template <typename T>
inline bool readn(T &x) {
  bool op = 0;
  char ch = getchar();
  x = 0;
  for (; !isdigit(ch) && ch != EOF; ch = getchar()) op ^= (ch == '-');
  if (ch == EOF) return false;
  for (; isdigit(ch); ch = getchar()) x = x * 10 + (ch ^ '0');
  if (op) x = -x;
  return true;
}
void rd() {}
void debug() { puts("*******************************"); }
