abc250E 判斷字首構成的集合是否相等

chenfy27發表於2024-03-18

給定陣列A[n]和B[n],有Q組詢問,每次給出一組(x,y),問A中前x個元素構成的集合是否與B中前y個元素構成的集合相等?
1<=n,q<=2e5; 1<=a[i],b[i]<=1e9; 1<=x[i],y[i]<=n

可以用乘法和異或來實現對集合的雜湊,另外需要藉助一個set來避免重複元素對雜湊結果的影響。

#include <bits/stdc++.h>
using namespace std;
#define int long long
#define rep(i,a,b) for(int i=a;i<=b;i++)
#define per(i,a,b) for(int i=b;i>=a;i--)

const int b1 = 409, m1 = 1000000409;
const int b2 = 439, m2 = 1000000439;
const int b3 = 433, m3 = 1000000433;
using hval = tuple<int,int,int>;

const int N = 200005;
int n, Q, a[N], b[N];
set<int> st1, st2;
hval A[N], B[N];
void solve() {
    cin >> n;
    rep(i,1,n) {
        cin >> a[i];
        A[i] = A[i-1];
        if (st1.count(a[i]))
            continue;
        st1.insert(a[i]);
        auto [x,y,z] = A[i-1];
        x ^= a[i] * b1;
        y ^= a[i] * b2;
        z ^= a[i] * b3;
        A[i] = {x,y,z};
    }
    rep(i,1,n) {
        cin >> b[i];
        B[i] = B[i-1];
        if (st2.count(b[i]))
            continue;
        st2.insert(b[i]);
        auto [x,y,z] = B[i-1];
        x ^= b[i] * b1;
        y ^= b[i] * b2;
        z ^= b[i] * b3;
        B[i] = {x,y,z};
    }
    cin >> Q;
    while (Q--) {
        int x, y;
        cin >> x >> y;
        if (A[x] == B[y])
            cout << "Yes\n";
        else
            cout << "No\n";
    }
}

signed main() {
    cin.tie(0)->sync_with_stdio(0);
    int t = 1;
    while (t--) solve();
    return 0;
}

相關文章