#include <bits/stdc++.h>
using namespace std;
vector<bool> mark;
vector<vector<int> > v;
vector<int> ds;
vector<long long> sz;
long long answer;
int n, aux;
bool g;
void dsBuild() {
  for (int i = 1; i <= n; i++) {
    ds[i] = i;
    sz[i] = 0;
  }
}
int dsFind(int i) {
  if (ds[i] != i) ds[i] = dsFind(ds[i]);
  return ds[i];
}
void dsUnion(int a, int b) {
  a = dsFind(a);
  b = dsFind(b);
  if (sz[a] < sz[b]) swap(a, b);
  if (a != b) {
    long long uj = ceil(double(sz[a]) / 2) + ceil(double(sz[b]) / 2) + 1;
    sz[a] = max(sz[a], sz[b]);
    sz[a] = max(sz[a], uj);
  }
  ds[b] = a;
}
void dfs(int u, int s) {
  mark[u] = true;
  if (s > answer) {
    answer = s;
    if (!g) aux = u;
  }
  for (auto i : v[u]) {
    if (!mark[i]) {
      dfs(i, s + 1);
    }
  }
}
int main() {
  ios::sync_with_stdio(0), cin.tie(0);
  int m, q, a, b;
  cin >> n >> m >> q;
  v.resize(n + 5);
  mark.assign(n + 5, false);
  ds.resize(n + 5);
  sz.resize(n + 5);
  dsBuild();
  while (m--) {
    cin >> a >> b;
    v[a].push_back(b);
    v[b].push_back(a);
    dsUnion(a, b);
  }
  for (int i = 1; i <= n; i++) {
    if (v[i].size() > 0) {
      if (ds[i] == i) {
        g = false;
        answer = 0;
        dfs(i, 0);
        g = true;
        mark.assign(n + 5, false);
        dfs(aux, 0);
        sz[dsFind(i)] = answer;
      }
    }
  }
  int x;
  while (q--) {
    cin >> x;
    if (x == 2) {
      cin >> a >> b;
      dsUnion(a, b);
    } else {
      cin >> a;
      cout << sz[dsFind(a)] << "\n";
    }
  }
  return 0;
}
