#include <bits/stdc++.h>
using namespace std;
template <class T>
inline void rd(T &x) {
  x = 0;
  char c = getchar();
  int f = 1;
  while (!isdigit(c)) {
    if (c == '-') f = -1;
    c = getchar();
  }
  while (isdigit(c)) x = x * 10 - '0' + c, c = getchar();
  x *= f;
}
const int N = 1e5 + 10;
map<int, int> col[N];
set<int> S[N], nxt[N];
int fa[N], n;
int find(int x) { return fa[x] == x ? x : fa[x] = find(fa[x]); }
void un(int x, int y) {
  int fx = find(x), fy = find(y);
  if (fx == fy) return;
  if (S[fx].size() > S[fy].size()) swap(fx, fy);
  for (set<int>::iterator it = S[fx].begin(); it != S[fx].end(); ++it) {
    nxt[*it].erase(fx), nxt[*it].insert(fy);
    S[fy].insert(*it);
  }
  fa[fx] = fy;
}
void adde(int x, int y, int w) {
  S[find(x)].insert(y), nxt[y].insert(find(x));
  S[find(y)].insert(x), nxt[x].insert(find(y));
  if (!col[x].count(w))
    col[x][w] = y;
  else
    un(y, col[x][w]);
  if (!col[y].count(w))
    col[y][w] = x;
  else
    un(x, col[y][w]);
}
int main() {
  int x, y, w, m, q;
  rd(n), rd(m), rd(x), rd(q);
  for (int i = 1; i <= n; ++i) fa[i] = i;
  for (int i = 1; i <= m; ++i) rd(x), rd(y), rd(w), adde(x, y, w);
  char op[10];
  while (q--) {
    scanf("%s", op);
    if (op[0] == '+')
      rd(x), rd(y), rd(w), adde(x, y, w);
    else {
      rd(x), rd(y);
      if (find(x) == find(y) || nxt[y].count(find(x)))
        printf("Yes\n");
      else
        printf("No\n");
    }
  }
  return 0;
}
