| 217 | |
| 218 | template <class mint, internal::is_static_modint_t<mint>* = nullptr> |
| 219 | std::vector<mint> convolution(std::vector<mint>&& a, std::vector<mint>&& b) { |
| 220 | int n = int(a.size()), m = int(b.size()); |
| 221 | if (!n || !m) return {}; |
| 222 | |
| 223 | int z = (int)internal::bit_ceil((unsigned int)(n + m - 1)); |
| 224 | assert((mint::mod() - 1) % z == 0); |
| 225 | |
| 226 | if (std::min(n, m) <= 60) return convolution_naive(std::move(a), std::move(b)); |
| 227 | return internal::convolution_fft(std::move(a), std::move(b)); |
| 228 | } |
| 229 | template <class mint, internal::is_static_modint_t<mint>* = nullptr> |
| 230 | std::vector<mint> convolution(const std::vector<mint>& a, |
| 231 | const std::vector<mint>& b) { |