#include<bits/stdc++.h> #include<atcoder/all> usingnamespace std; usingnamespace atcoder; using mint = modint998244353; #ifdef LOCAL #define debug(...) fprintf(stdout, ##__VA_ARGS__) #else #define debug(...) void(0) #endif //#define int long long inlineintread(){int x=0,f=1;char ch=getchar(); while(ch<'0'||ch>'9'){if(ch=='-')f=-1; ch=getchar();}while(ch>='0'&&ch<='9'){x=(x<<1)+ (x<<3)+(ch^48);ch=getchar();}return x*f;} #define Z(x) (x)*(x) #define pb push_back #define fi first #define se second //#define M //#define mo #define N 200010 int n, m, i, j, k, T; int X[N], Y[N], lim, pk;
signedmain() { #ifdef LOCAL freopen("in.txt", "r", stdin); freopen("out.txt", "w", stdout); #endif // srand(time(NULL)); // T = read(); // while(T--) { // // } n = read(); for(i = 1; i <= n; ++i) k = read(), X[k]++; for(i = 1; i <= n; ++i) k = read(), Y[k]++; for(i = 1; i <= n; ++i) debug("%lld ", X[i]); debug("\n"); for(i = 1; i <= n; ++i) debug("%lld ", Y[i]); debug("\n"); vector<mint> fac(N), ifac(N); for(i = 1, fac[0] = 1; i <= n; ++i) fac[i] = fac[i - 1] * i; ifac[n] = fac[n].inv(); for(i = n; i >= 1; --i) ifac[i - 1] = ifac[i] * i; auto C = [&] (int n, int r) -> mint { if(r < 0 || r > n) return0; return fac[n] * ifac[r] * ifac[n - r]; }; vector<vector<mint> > polys; for(k = 1; k <= n; ++k) { if((lim = min(X[k], Y[k])) == 0) continue; vector<mint>poly(lim + 1); for(i = 0, pk = 1; i <= lim; ++i, pk = - pk) { mint cnt = pk * C(X[k], i) * C(Y[k], i) * fac[i]; poly[i] = cnt; } polys.pb(poly); } auto cmp = [&] (const vector<mint>& a, const vector<mint>& b) { return a.size() > b.size(); }; priority_queue<vector<mint>, vector<vector<mint> >, decltype(cmp)> q(cmp); for(auto& p : polys) q.push(p); vector<mint> f; if(q.empty()) f = {1}; else { while(q.size() > 1) { auto a = q.top(); q.pop(); auto b = q.top(); q.pop(); auto c= convolution(a, b); q.push(c); } f = q.top(); } mint ans = 0; for(i = 0; i < (int)f.size(); ++i) ans += f[i] * fac[n - i]; ans = ans * ifac[n]; cout << ans.val(); return0; }