Bluestein’s Algorithm is an algorithm that computes for a polynomial in time and space.
Algorithm
Lemma
Let
then
Proof
- Let . Apply the Fast Fourier Transform to find and .
- Use the results from 0 to find .
- Apply the Inverse Fast Fourier Transform to find .
- For each in , apply the lemma to find .
This algorithm solves the problem in time and space.
std::vector<std::complex<double>> bluestein(int n, const std::vector<std::complex<double>> &a, std::complex<double> z, int m) {
auto f = std::ranges::to<std::vector>(std::views::iota(0, n) | std::views::transform([&](int i) -> std::complex<double> {
return a[i] / std::pow(z, 1. * i * i / 2);
}) | std::views::reverse), g = std::ranges::to<std::vector>(std::views::iota(0, n + m) | std::views::transform([&](int i) -> std::complex<double> {
return std::pow(z, 1. * i * i / 2);
}));
int k = std::bit_ceil<u32>(2 * n + m - 1);
f.resize(k, 0), g.resize(k, 0);
fft(k, f), fft(k, g);
for (int i = 0; i < k; i++) {
f[i] *= g[i];
}
ifft(k, f);
return std::ranges::to<std::vector>(std::views::iota(0, m) | std::views::transform([&](int i) -> std::complex<double> {
return f[n - 1 + i] / std::pow(z, 1. * i * i / 2);
}));
}