template <uint64_t mod> constexpruint64_tinverse(uint64_t x){ uint64_t res = 1, b = mod - 2; for (x %= mod; b; b >>= 1, x = x * x % mod) if (b & 1) res = res * x % mod; return res; }
template <bool inv = false, uint64_t mod = 0> voidFWT_xor(vector<uint64_t> &arr) { size_t n = arr.size(); for (size_t k = 1; k < n; k <<= 1) { for (size_t i = 0; i < n; i += k << 1) { for (size_t j = 0; j < k; ++j) { uint64_t u = arr[i + j], v = arr[i + j + k]; arr[i + j] = u + v; arr[i + j + k] = mod + u - v; ifconstexpr(mod != 0) arr[i + j] %= mod, arr[i + j + k] %= mod; ifconstexpr(inv){ ifconstexpr(mod == 0) arr[i + j] >>= 1, arr[i + j + k] >>= 1; else { staticconstexpruint64_t inv2 = inverse<mod>(2); arr[i + j] = arr[i + j] * inv2 % mod; arr[i + j + k] = arr[i + j + k] * inv2 % mod; } } } } } }