#include <bits/stdc++.h>
using namespace std;
long long power(long long b, long long p) {
  long long res = 1;
  while (p) {
    if (p % 2) {
      res = (res * b) % 1000000007;
      p--;
    } else {
      b = (b * b) % 1000000007;
      p /= 2;
    }
  }
  return res;
}
void update(int node, int start, int end, int idx, int val, vector<int> &tree) {
  if (start == end) {
    tree[node] = val;
    return;
  }
  int mid = (start + end) / 2;
  if (idx >= start && idx <= mid)
    update(2 * node, start, mid, idx, val, tree);
  else
    update(2 * node + 1, mid + 1, end, idx, val, tree);
  tree[node] = max(tree[2 * node], tree[2 * node + 1]);
}
int query(int node, int start, int end, int l, int r, vector<int> &tree) {
  if (r < start || l > end) return 0;
  if (start >= l && end <= r) return tree[node];
  int mid = (start + end) / 2;
  return max(query(2 * node, start, mid, l, r, tree),
             query(2 * node + 1, mid + 1, end, l, r, tree));
}
long long f, c;
void dfs(long long r, vector<vector<long long> > &v,
         vector<vector<long long> > &e, vector<long long> &vis, long long s) {
  vis[r] = s;
  c++;
  for (long long i = 0; i < e[r].size(); i++)
    if (vis[e[r][i]] == vis[r]) f = 1;
  for (long long i = 0; i < v[r].size(); i++)
    if (!vis[v[r][i]]) dfs(v[r][i], v, e, vis, s);
}
int main() {
  long long n, m, k, i, ans = 0, a, b;
  cin >> n;
  vector<long long> vis(n + 1);
  vector<vector<long long> > v(n + 1), e(n + 1);
  cin >> k;
  while (k--) {
    cin >> a >> b;
    v[a].push_back(b);
    v[b].push_back(a);
  }
  cin >> m;
  while (m--) {
    cin >> a >> b;
    e[a].push_back(b);
    e[b].push_back(a);
  }
  for (i = 1; i <= n; i++) {
    if (!vis[i]) {
      f = 0, c = 0;
      dfs(i, v, e, vis, i);
      if (!f) ans = max(ans, c);
    }
  }
  cout << ans;
}
