diff --git a/atcoder/convolution.hpp b/atcoder/convolution.hpp index 69c2654..04cc20f 100644 --- a/atcoder/convolution.hpp +++ b/atcoder/convolution.hpp @@ -34,7 +34,7 @@ void butterfly(std::vector& a) { ie *= ie; } mint now = 1; - for (int i = 0; i < cnt2 - 2; i++) { + for (int i = 0; i <= cnt2 - 2; i++) { sum_e[i] = es[i] * now; now *= ies[i]; } @@ -76,7 +76,7 @@ void butterfly_inv(std::vector& a) { ie *= ie; } mint now = 1; - for (int i = 0; i < cnt2 - 2; i++) { + for (int i = 0; i <= cnt2 - 2; i++) { sum_ie[i] = ies[i] * now; now *= es[i]; } diff --git a/test/unittest/convolution_test.cpp b/test/unittest/convolution_test.cpp index e20f912..370d00a 100644 --- a/test/unittest/convolution_test.cpp +++ b/test/unittest/convolution_test.cpp @@ -3,6 +3,7 @@ #include #include #include +#include "../utils/random.hpp" using namespace atcoder; using uint = unsigned int; @@ -353,3 +354,33 @@ TEST(ConvolutionTest, ConvLLBound) { ASSERT_EQ(a, convolution_ll(a, b)); } } + +// https://github.com/atcoder/ac-library/issues/30 +TEST(ConvolutionTest, Conv641) { + // 641 = 128 * 5 + 1 + const int MOD = 641; + std::vector a(64), b(65); + for (int i = 0; i < 64; i++) { + a[i] = randint(0, MOD - 1); + } + for (int i = 0; i < 65; i++) { + b[i] = randint(0, MOD - 1); + } + + ASSERT_EQ(conv_naive(a, b), convolution(a, b)); +} + +// https://github.com/atcoder/ac-library/issues/30 +TEST(ConvolutionTest, Conv18433) { + // 18433 = 2048 * 9 + 1 + const int MOD = 18433; + std::vector a(1024), b(1025); + for (int i = 0; i < 1024; i++) { + a[i] = randint(0, MOD - 1); + } + for (int i = 0; i < 1025; i++) { + b[i] = randint(0, MOD - 1); + } + + ASSERT_EQ(conv_naive(a, b), convolution(a, b)); +}