#pragma region Yoyoyo #ifdef LOCAL #define _GLIBCXX_DEBUG #endif #include using namespace std; using ll=long long; using ld=long double; using i128t=__int128_t; using pii=pair; using pll=pair; const string Yes="Yes"; const string No="No"; const long long inf=1ll<<60; #ifndef LOCAL #pragma GCC target("avx2") #pragma GCC optimize("O3") #pragma GCC optimize("unroll-loops") #endif #define fi first #define se second #define pb push_back #define eb emplace_back #define mp make_pair #define all(x) (x).begin(),(x).end() #define faster ios::sync_with_stdio(false);cin.tie(nullptr); #define print(s) cout< inline bool chmax(T &a,T b){return ((a inline bool chmin(T &a,T b){return ((a>b)?(a=b,true):(false));} template ll sum(const T&a){return accumulate(all(a),0LL);} template ostream &operator<<(ostream &os,const pair&p){ os< istream &operator>>(istream &is,pair&p){ is>>p.first>>p.second; return is; } template ostream &operator<<(ostream &os,const vector&v){ int s=v.size(); for(int i=0;i istream &operator>>(istream &is,vector&v){ for(auto &x:v){ is>>x; } return is; } template ostream &operator<<(ostream &os,const vector>&v){ int s=v.size(); for(int i=0;i ostream &operator<<(ostream &os,const vector>>&v){ int s=v.size(); for(int i=0;i par, rank, siz; // 構造体の初期化 UnionFind(long long n) : par(n, -1), rank(n, 0), siz(n, 1) {} // 根を求める long long root(long long x) { if (par[x] == -1) return x; // x が根の場合は x を返す else return par[x] = root(par[x]); // 経路圧縮 } // x と y が同じグループに属するか (= 根が一致するか) bool same(long long x, long long y) { return root(x) == root(y); } // x を含むグループと y を含むグループを併合する bool unite(long long x, long long y) { int rx = root(x), ry = root(y); // x 側と y 側の根を取得する if (rx == ry) return false; // すでに同じグループのときは何もしない // union by rank if (rank[rx] < rank[ry]) swap(rx, ry); // ry 側の rank が小さくなるようにする par[ry] = rx; // ry を rx の子とする if (rank[rx] == rank[ry]) rank[rx]++; // rx 側の rank を調整する siz[rx] += siz[ry]; // rx 側の siz を調整する return true; } // x を含む根付き木のサイズを求める long long size(long long x) { return siz[root(x)]; } }; int main(){ faster; ll N,M,X,K; cin>>N>>M>>X>>K; { assert(2<=N && N<=200000); assert(1<=M && M<=N*(N-1)/2 && M<=200000); assert(1<=X && X<=1000000000); assert(2<=K && K<=N); } vectorA(N); cin>>A; vector>G(N); for(int i=0;i>u>>v; u--;v--; if(abs(A[u]-A[v])>X)continue; G[u].pb(mp(v,i)); G[v].pb(mp(u,i)); } for(int i=0;i