#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>
#include <ext/pb_ds/detail/standard_policies.hpp>

using namespace std;
using namespace __gnu_pbds;
//-------------------------------------------//
#define int long long
//-------------------------------------------//
#pragma GCC optimize("O3")
//-------------------------------------------//
#define pii pair<int, int>
#define ft first
#define sd second
#define fast                      \
    ios_base::sync_with_stdio(0); \
    cin.tie(0)
#define cout_float cout.setf(ios::fixed); cout.precision(20)
//-------------------------------------------//
typedef long long ll;
typedef long double ld;
typedef tree<int,
null_type,
less<int>,
rb_tree_tag,
tree_order_statistics_node_update> ordered_set;
//---------------------------------------------------------------------------------------//

struct Node {
    int value;
    int size;

    Node* left = nullptr;
    Node* right = nullptr;

    Node(int x): value(x), size(1) {}
};

int size(Node* N) {
    if (!N) return 0;
    return N->size;
}

void upd(Node* N) {
    N->size = size(N->left) + size(N->right);
}

Node* merge(Node* L, Node* R) {
    if (!L) return R;
    if (!R) return L;
    if (rand() % (L->size + R->size) < L->size) {
        L->right = merge(L->right, R);
        upd(L);
        return L;
    } else {
        R->left = merge(L, R->left);
        upd(R);
        return R;
    }
}

pair<Node*, Node*> splitV(Node* rt, int x) { //left - strictly less than x
    if (!rt) return {nullptr, nullptr};
    if (rt->value >= x) {
        pair<Node*, Node*> p = splitV(rt->left, x);
        rt->left = p.second;
        upd(rt);
        return {p.first, rt};
    } else {
        pair<Node*, Node*> p = splitV(rt->right, x);
        rt->right = p.first;
        upd(rt);
        return {rt, p.second};
    }
}

pair<Node*, Node*> splitI(Node* rt, int k) { //exactly k nodes in the left part
    if (!rt) return {nullptr, nullptr};
    if (size(rt->left) >= k) {
        pair<Node*, Node*> p = splitI(rt->left, k);
        rt->left = p.second;
        upd(rt);
        return {p.first, rt};
    } else {
        pair<Node*, Node*> p = splitI(rt->right, k - size(rt->left) - 1);
        rt->right = p.first;
        upd(rt);
        return {rt, p.second};
    }
}

//Node* root = nullptr;

//-----------------------------------------------------------------------------------------//

struct segtree {
    int size = 1;
    vector<int> tree;

    void init(int n) {
        while (size < n) size *= 2;
        tree.assign(2 * size - 1, 0);
    }

    void upd(int x, int lx, int rx) {
        if (rx - lx == 1) return;
        tree[x] = tree[2 * x + 1] + tree[2 * x + 2];
    }

    void build(vector<int> &a, int x, int lx, int rx) {
        if (rx - lx == 1) {
            if (lx < (int)a.size()) {
                tree[x] = a[lx];
            }
            return;
        }
        int mx = (lx + rx) / 2;
        build(a, 2 * x + 1, lx, mx);
        build(a, 2 * x + 2, mx, rx);
        upd(x, lx, rx);
    }

    void build(vector<int> &a) {
        init((int)a.size());
        build(a, 0, 0, size);
    }

    void set(int i, int v, int x, int lx, int rx) {
        if (rx - lx == 1) {
            tree[x] = v;
            return;
        }
        int mx = (lx + rx) / 2;
        if (i < mx) {
            set(i, v, 2 * x + 1, lx, mx);
        } else {
            set(i, v, 2 * x + 2, mx, rx);
        }
        upd(x, lx, rx);
    }

    void set(int i, int v) {
        set(i, v, 0, 0, size);
    }

    int get_sum(int l, int r, int x, int lx, int rx) {
        if (r <= lx || rx <= l) {
            return 0;
        }
        if (l <= lx && rx <= r) {
            return tree[x];
        }
        int mx = (lx + rx) / 2;
        int s1 = get_sum(l, r, 2 * x + 1, lx, mx);
        int s2 = get_sum(l, r, 2 * x + 2, mx, rx);
        return s1 + s2;
    }

    int get_sum(int l, int r) {
        return get_sum(l, r, 0, 0, size);
    }
};

//------------------------------------------------------------------//

struct node {
    int sum;

    node* left = nullptr;
    node* right = nullptr;

    node(int x): sum(x) {}
    node(): sum(0) {}
    node(node* L, node* R): sum(L->sum + R->sum) {}
};

int sz = 1;

void init(int n) {
    while (sz < n) sz *= 2;
}

node* build(vector<int> &a, int lx, int rx) {
    if (rx - lx == 1) {
        if (lx < (int)a.size()) {
            return new node(a[lx]);
        } else {
            return new node();
        }
    }
    int mx = (lx + rx) / 2;
    return new node(build(a, lx, mx), build(a, mx, rx));
}

node* build(vector<int> &a) {
    init((int)a.size());
    return build(a, 0, sz);
}

node* setT(int i, int v, int lx, int rx, node* cur) {
    if (rx - lx == 1) {
        return new node(v);
    }
    int mx = (lx + rx) / 2;
    if (i < mx) {
        return new node(setT(i, v, lx, mx, cur->left), cur->right);
    } else {
        return new node(cur->left, setT(i, v, mx, rx, cur->right));
    }
}

int get_sum(int l, int r, int lx, int rx, node* cur) {
    if (r <= lx || rx <= l) {
        return 0;
    }
    if (l <= lx && rx <= r) {
        return cur->sum;
    }
    int mx = (lx + rx) / 2;
    int s1 = get_sum(l, r, lx, mx, cur->left);
    int s2 = get_sum(l, r, mx, rx, cur->right);
    return s1 + s2;
}

//node* versions[q + 1];
//versions[0] = build(a);
//versions[i + 1] = setT(j, val, 0, sz, versions[i]);
//to get sum -> get_sum(l, r, 0, sz, versions[query]);

//-----------------------------------------------------------------------//

signed main() {
    fast;
    freopen("input.txt", "r", stdin);
    int N, n, M, m, k, q;
    cin >> N >> n >> M >> m >> k >> q;
    vector<int> lena(n), lenb(m);
    vector<int> vala(n), valb(m);
    vector<int> prefsa(n + 1, 0), prefsb(m + 1, 0);
    int A[N], B[M];
    for (int i = 0; i < n; ++i) {
        cin >> lena[i] >> vala[i];
        //Abv[vala[i]] = i;
        prefsa[i + 1] = prefsa[i] + lena[i];
        for (int j = prefsa[i]; j < prefsa[i + 1]; ++j) A[j] = vala[i];
    }
    for (int i = 0; i < m; ++i) {
        cin >> lenb[i] >> valb[i];
        //[valb[i]] = i;
        prefsb[i + 1] = prefsb[i] + lenb[i];
        for (int j = prefsb[i]; j < prefsb[i + 1]; ++j) B[j] = valb[i];
    }

    int nextoA[N], nextoB[M];
    nextoA[N - 1] = N;
    for (int iA = N - 2; iA >= 0; --iA) {
        if (A[iA] != A[iA + 1]) {
            nextoA[iA] = iA + 1;
        } else {
            nextoA[iA] = nextoA[iA + 1];
        }
    }
    nextoB[M - 1] = M;
    for (int iB = M - 2; iB >= 0; --iB) {
        if (B[iB] != B[iB + 1]) {
            nextoB[iB] = iB + 1;
        } else {
            nextoB[iB] = nextoB[iB + 1];
        }
    }


    int closeA[N][k + 1];
    int closeB[M][k + 1];
    for (int p = 1; p <= k; ++p) {
        int lastA = N;
        for (int iA = N - 1; iA >= 0; --iA) {
            closeA[iA][p] = lastA;
            if (A[iA] == p) lastA = iA;
        }
        int lastB = M;
        for (int iB = M - 1; iB >= 0; --iB) {
            closeB[iB][p] = lastB;
            if (B[iB] == p) lastB = iB;
        }
    }

    int dp[N + 1][M + 1];
    for (int iB = M; iB >= 0; --iB) {
        dp[N][iB] = 0;
    }
    for (int iA = N; iA >= 0; --iA) {
        dp[iA][M] = 0;
    }
    for (int iA = N - 1; iA >= 0; --iA) {
        for (int iB = M - 1; iB >= 0; --iB) {
            if (A[iA] != B[iB]) {
                if (closeB[iB][A[iA]] < M && dp[iA + 1][closeB[iB][A[iA]] + 1] == 0) {
                    dp[iA][iB] = 1;
                } else {
                    dp[iA][iB] = dp[nextoA[iA]][iB];
                }
            } else {
                if (dp[iA + 1][iB + 1] == 0) {
                    dp[iA][iB] = 1;
                } else {
                    //since stalling loses, we'll do a different turn!
                    dp[iA][iB] = dp[nextoA[iA]][nextoB[iB]];
                }
            }
        }
    }
    while (q--) {
        int x, y;
        cin >> x >> y;
        if (dp[x][y]) {
            cout << "Yes\n";
        } else {
            cout << "No\n";
        }
    }
    return 0;
}
