answer:
April did when YY training DAG count, and this is basically the same, but the violence was like a subset of direct convolution, when the province otherwise the election will not will not, on this side is not more than a selected subset of probability and convolution.
DAG is routine to count the use of the DAG is 0-degree point.
Set \ (f [S] \) represents only consider FIG elicitor s in the number of dots formed embodiment of the DAG.
Enumeration a \ (T | S ~ \ ~ and T = \ empty \) , this is the new T in FIG degree point 0, there is no edge between them first, then \ (T \) and \ (S \) side between either absent or consists of \ (T-> S \) , denoted \ (CNT [S] \) represents S in the number of edges, which transfer coefficient is:
\ ({. 1 \} ^ over. 3 {g [T]} * { {2 \ over 3} ^ {g [S + T]} \ over {2 \ over 3} ^ {g [S] + g {T}}} \)
Note that this weight will be counted, because the degree to enumerate the subset of point 0, then the exclusion capacity coefficient \ ((-. 1) ^ {| T | + 1'd} \) , consider \ (\ sum_ {i = 1} ^ {| T |} (- 1) ^ {i + 1} * C_ {| T |} ^ i = 1 \) to prove.
Direct convolution is \ (O (n-^. 3) \) , then the old routine or FWT + 1 is the number, complexity \ (O (n-2 ^ ^ * n-2) \) .
Code:
#include<bits/stdc++.h>
#define fo(i, x, y) for(int i = x, B = y; i <= B; i ++)
#define ff(i, x, y) for(int i = x, B = y; i < B; i ++)
#define fd(i, x, y) for(int i = x, B = y; i >= B; i --)
#define ll long long
#define pp printf
#define hh pp("\n")
using namespace std;
const int mo = 998244353;
ll ksm(ll x, ll y) {
ll s = 1;
for(; y; y /= 2, x = x * x % mo)
if(y & 1) s = s * x % mo;
return s;
}
const ll w1 = ksm(3, mo - 2), w2 = 2 * ksm(3, mo - 2) % mo;
const ll nw1 = ksm(w1, mo - 2), nw2 = ksm(w2, mo - 2);
const int N = 21;
const int M = 1 << 20;
int n, m, x, y, a2[N];
int bz[N][N];
ll f[M], nf[M], g[M];
int cnt[M];
void dft(int *a, int n, int f) {
for(int h = 1; h < n; h *= 2) for(int j = 0; j < n; j += 2 * h) ff(i, 0, h) {
if(f == 1) a[i + j + h] = (a[i + j + h] + a[i + j]) % mo; else
a[i + j + h] = (a[i + j + h] - a[i + j]) % mo;
}
}
int a[21][M], b[21][M];
int main() {
scanf("%d %d", &n, &m);
a2[0] = 1; fo(i, 1, n) a2[i] = a2[i - 1] * 2;
fo(i, 1, m) {
scanf("%d %d", &x, &y);
x --; y --;
bz[x][y] = 1;
}
ff(s, 1, a2[n]) cnt[s] = cnt[s - (s & -s)] + 1;
ff(s, 0, a2[n]) {
f[s] = g[s] = nf[s] = 1;
if(s == 0) continue;
int st;
ff(i, 0, n) if(s >> i & 1) { st = i;}
f[s] = f[s ^ (1 << st)];
g[s] = g[s ^ (1 << st)];
nf[s] = nf[s ^ (1 << st)];
ff(i, 0, st) if(s >> i & 1) {
if(bz[st][i]) f[s] = f[s] * w2 % mo, nf[s] = nf[s] * nw2 % mo, g[s] = g[s] * w1 % mo;
if(bz[i][st]) f[s] = f[s] * w2 % mo, nf[s] = nf[s] * nw2 % mo, g[s] = g[s] * w1 % mo;
}
}
fo(i, 1, n) {
ff(j, 0, a2[n]) if(cnt[j] == i)
b[i][j] = nf[j] * g[j] % mo * ((cnt[j] & 1) ? 1 : -1);
dft(b[i], a2[n], 1);
}
a[0][0] = 1; dft(a[0], a2[n], 1);
fo(w, 0, n) {
fo(j, 1, n - w) {
ff(i, 0, a2[n]) a[j + w][i] = ((ll) a[w][i] * b[j][i] + a[j + w][i]) % mo;
}
}
dft(a[n], a2[n], -1);
ll ans = a[n][a2[n] - 1];
ans = (ans % mo + mo) * f[a2[n] - 1] % mo;
pp("%lld\n", ans);
}