已知多項式f(x)=a0+a1x+a2x2+...+am-1xm-1, g(x)=b0+b1x+b2x2+...+bn-1xn-1。利用卷積的蠻力算法,得到h(x)=f(x)g(x),這一過程的時間復雜度為O(n2)。但是,利用分治策略和插值法來求解h(x),可以將時間復雜度降低至O(nlogn),從而大幅提升算法的效率。此求值算法將被應用於FFT算法中。
一、多項式求值
首先,由lagrange插值法可以知道,對於一個n-1次多項式,只要給定n個不同的點(xi, yi),我們就可以計算出多項式的系數。因此,求解2n-1次多項式系數的問題,可以轉化為多項式對1的復數域中所有2n次方根求值的問題。其中,1在復數域的2n次方根可以表示為

設f(x),g(x)為n-1次多項式,則插值法求多項式h(x)=f(x)g(x)的系數的步驟如下:
- 選擇2n個不同的值xj(j=0,1,...,2n-1),求出算f(xj),g(xj)
- 計算所有h(xj)=f(xj)g(xj)
- 由於h(x)的次數不高於2n-1,利用lagrange插值公式求出h(x)的系數
在第一步多項式求值過程中,如果用蠻力算法,即直接計算每一個A(wj),那么時間復雜度為O(n3)。但事實上,設Ak(x)=an-k+an-k+1x+...+an-1xk-1,則存在關系:
Ak(x)=an-k+xAk-1(x)
利用這一遞推關系式來求解A(x)=An(x),復雜度可以降低到O(n2)。這比蠻力算法已經有了很大的改進,但有沒有更高效的求值算法呢?
采用分治策略,可以將多項式求值過程的時間復雜度降低至O(nlogn),從而大幅提升算法的效率。這一算法的思想如下:
設要求值的多項式為A(x)=a0+a1x+...+an-1xn-1,不妨設n為偶數,令
A0(x)=a0+a2x+a4x2+...+an-2x(n-2)/2
A1(x)=a1+a3x+a5x2+...+an-1x(n-2)/2
則
A(x)=A0(x2)+xA1(x2)
值得注意的是,根據復數域2n次單位根的性質,x2並不需要重新計算,只要在單位圓上間隔取值就可以了。下面給出用分治策略為多項式求值的算法偽碼
算法1 Polyval(A, W) //分治策略多項式求值(假設n為偶數)
輸入:n-1次多項式A的系數a0,a1,...,an-1,以及w0,w1,...,w2n-1
輸出:A(w0),A(w1),...,A(w2n-1)
1. if A的長度=1 return A(W)
2. else do
3. 計算W1: W[0]2,W[1]2,...,W[2n-1]2
4. 計算A0: A[0],A[2],...A[n-2]
5. 計算A1: A[1],A[3],...A[n-1]
6. A0(W1)←Polyval(A0, W1)
7. A1(W1)←Polyval(A1, W1)
8. return A(W)=A0(W1)+WTA1(W1)
算法的遞推方程為T(n) = 2T(n/2) + f(n), T(1) = O(1)。其中,f(n)為初始時計算所有2n次方根的時間,f(n) = O(n)。根據主定理,得到T(n) = O(nlogn)。
二、快速傅立葉變換
設f(x)=a0+a1x+a2x2+...+an-1xn-1, g(x)=b0+b1x+b2x2+...+bn-1xn-1,h(x)=f(x)g(x)。下面給出FFT算法的偽碼:
算法2 FFT
1. 對x=wj(j=0,1,...,2n-1),分別計算f(wj),g(wj)
2. 利用步驟1的結果,計算所有dj=h(wj)
3. 構造多項式D(x)=d0+d1x+d2x2+...+d2n-1x2n-1
4. 對x=wj(j=0,1,...,2n-1),計算D(wj)
5. 設h(x)的系數為c0,c1,...,c2n-1,則有c0=D(1)/2n,c2n-1=D(w1)/2n,...,c1=D(w2n-1)/2n
不難分析,FFT算法時間復雜度為O(nlogn)。
