写在之前
因为想要补周五的ECFinal pk赛中2017-2018 ACM-ICPC, Asia Daejeon Regional Contest Rock Paper Scissors,所以打算学习一下FFT的相关知识。然后一不小心看到了很多聚聚们写的其他相关博客,因而又发现了一片有趣的天地所以打算逐渐学习一下多项式全家桶。
FFT 快速傅立叶变换
很多博客的算法都是知其然不知其所以然,我认为自为风月马前卒dalao的这一篇博客写的很漂亮
(因为在处理范德蒙德行列式的逆的时候用到了一种蒙人的做法所以很干净简洁)
先大体用我粗糙的语言描述一下我对FFT算法的理解:
一个 n − 1 n - 1 n−1阶的多项式具有 n n n个自由变量,也就是说只需要用 n n n个自由量就可以进行刻画该多项式。我们所熟悉的表示办法是用 n n n个系数进行刻画,但是这种表示办法在计算多项式乘法的时候时间复杂度 O ( n 2 ) O(n^2) O(n2)不可接受,所以我们考虑用一种更有利的表示来加速多项式乘法。我们按照一定的规律在多项式上选取 n n n个值,用这 n n n个值来刻画多项式。问题的要害在于如何选取对应的 x [ i ] x[i] x[i]可以使得对应的 n n n个值既好求又具有一些便利的性质可以方便我们的计算。
FFT算法的提出者使用了 n n n阶单位根作为 x x x的取值,即 x [ i ] = w n i , i = 0 , 1 , x[i] = w_n^i,i = 0,1, x[i]=wni,i=0,1, ⋯ \cdots ⋯ , n − 1 ,n -1 ,n−1.再分离奇偶项将原多项式化归成两个小多项式的和,利用单位根的性质即可在 O ( n l o g n ) O(nlogn) O(nlogn)的时间下将系数多项式转化为点值多项式。之后可以将两个多项式进行 O ( n ) O(n) O(n)的乘法获得乘积多项式。
之后的问题就是如何将点值多项式还原到系数多项式,这个过程称为傅立叶逆变换。事实上,我们构造一个n阶矩阵,可以表示出从自变量到因变量之间的变换关系,容易发现这个n阶矩阵是一个范德蒙德矩阵,其中 x i xi xi分别一一被取为 n n n次单位根中的一个。
盗来的图:
那么如何从因变量和变换关系求得自变量?那自然是对矩阵取逆。该矩阵有一个优良的性质,就是其逆恰好为每一项取共轭再以 n n n,证明方法我不会…因为偷瞄了一眼感觉很复杂的亚子就没有看下去。不过在这个问题的严谨证明上,自为风月马前卒给出了一种办法。
设 ( y 1 , y 2 , . . . , y n