#include <bits/stdc++.h>
using namespace std;
typedef struct {
  int r;
  int a;
  int id;
  int massimo;
} membro;
vector<membro> tree[4 * 100010];
vector<int> s[4 * 100010];
vector<int> d[4 * 100010];
membro m[100010];
membro m1[100010];
membro indici[100010];
int n, k, q;
bool cmp1(membro const& x, membro const& y) {
  if (x.r == y.r) return x.massimo < y.massimo;
  return x.r < y.r;
}
bool cmp(membro const& x, membro const& y) { return x.a < y.a; }
void build_massimo(int p, int left, int right, int ctrl) {
  int i, mid = (left + right) / 2;
  if (left != right) {
    tree[p * 2].clear();
    tree[p * 2 + 1].clear();
    s[p].clear();
    d[p].clear();
    for (i = 0; i < (int)tree[p].size(); i++) {
      s[p].push_back(tree[p * 2].size());
      d[p].push_back(tree[p * 2 + 1].size());
      if (tree[p][i].id <= mid)
        tree[p * 2].push_back(tree[p][i]);
      else
        tree[p * 2 + 1].push_back(tree[p][i]);
    }
    s[p].push_back(tree[p * 2].size());
    d[p].push_back(tree[p * 2 + 1].size());
    build_massimo(p * 2, left, mid, ctrl);
    build_massimo(p * 2 + 1, mid + 1, right, ctrl);
  }
  if (ctrl) {
    for (i = tree[p].size() - 2; i >= 0; i--)
      tree[p][i].massimo = max(tree[p][i].massimo, tree[p][i + 1].massimo);
  }
}
int massimo(int p, int left, int right, int l, int r, int cerca, int ctrl) {
  if (m[left].a > r || m[right].a < l || l > r) {
    if (!ctrl) return 0;
    return -1;
  }
  if (ctrl && cerca == (int)tree[p].size()) return -1;
  if (m[left].a >= l && m[right].a <= r) {
    if (!ctrl) return cerca;
    return tree[p][cerca].massimo;
  }
  int mid = (left + right) / 2;
  int a = massimo(p * 2, left, mid, l, min(m[mid].a, r), s[p][cerca], ctrl);
  int b = massimo(p * 2 + 1, mid + 1, right, max(m[mid + 1].a, l), r,
                  d[p][cerca], ctrl);
  if (!ctrl) return a + b;
  return max(a, b);
}
int main() {
  int i;
  scanf("%d %d", &n, &k);
  for (i = 0; i < n; i++) scanf("%d", &m[i].r);
  for (i = 0; i < n; i++) scanf("%d", &m[i].a);
  for (i = 0; i < n; i++) indici[i + 1] = m[i];
  sort(m, m + n, cmp);
  for (i = 0; i < n; i++) {
    m[i].id = i;
    m1[i] = m[i];
  }
  sort(m1, m1 + n, cmp1);
  for (i = 0; i < n; i++) tree[1].push_back(m1[i]);
  build_massimo(1, 0, n - 1, 0);
  for (i = 0; i < n; i++) {
    membro temp;
    temp.massimo = 100010;
    temp.r = m1[i].r;
    int cerca = upper_bound(tree[1].begin(), tree[1].end(), temp, cmp1) -
                tree[1].begin();
    m1[i].massimo = massimo(1, 0, n - 1, m1[i].a - k, m1[i].a + k, cerca, 0);
  }
  sort(m1, m1 + n, cmp1);
  for (i = 0; i < n; i++) tree[1][i] = m1[i];
  build_massimo(1, 0, n - 1, 1);
  scanf("%d", &q);
  for (i = 0; i < q; i++) {
    int x, y;
    scanf("%d %d", &x, &y);
    membro temp;
    temp.massimo = 0;
    temp.r = max(indici[x].r, indici[y].r);
    int cerca = lower_bound(tree[1].begin(), tree[1].end(), temp, cmp1) -
                tree[1].begin();
    printf("%d\n", massimo(1, 0, n - 1, max(indici[x].a, indici[y].a) - k,
                           min(indici[x].a, indici[y].a) + k, cerca, 1));
  }
  return 0;
}
