傅里叶拟合系数

时间:2015-11-01 00:11:59

标签: python

最近我一直在为一个周期信号拟合傅立叶级数函数,以便通过最小二乘法检索每个分量的幅度和相位,所以我修改了this文件的代码:

import math
import numpy as np
#period of the signal
per=1.0
w = 2.0*np.pi/per
#number of fourier components.
nf = 5
fp = open("file.cat","r")
# m1 is the number of unknown coefficients.
m1 = 2*nf + 1
# Create empty matrices.
x = np.zeros((m1,m1))
y = np.zeros((m1,1))
xi = [0.0]*m1

# Read (time, value) from each line of the file.
for line in fp:
    t = float(line.split()[0])
    yi = float(line.split()[1])
    xi[0] = 1.0
    for k in range(1,nf+1):
        xi[2*k-1] = np.sin(k*w*t)
        xi[2*k] = np.cos(k*w*t)
    for j in range(m1):
        for k in range(m1):
            x[j,k] += xi[j]*xi[k]
        y[j] += yi*xi[j]
fp.close()
# Copy to big matrices.
X = np.mat( x.copy() )
Y = np.mat( y.copy() )
# Invert X and multiply by Y to get coefficients.
A = X.I*Y
A0 = A[0]
# Solution is A0 + Sum[ Amp*sin(k*wt + phi) ]
print "a[0] = %f" % A[0]
for k in range(1,nf+1):
    amp = math.sqrt(A[2*k-1]**2 + A[2*k]**2)
    phs = math.atan2(A[2*k],A[2*k-1])
    print "amp[%d] = %f phi = %f" % (k, amp, phs)

但情节显示了这一点(当然没有分数):

enter image description here

它应该显示如下:

enter image description here

有人可以告诉我如何以另一种更简单的方式计算相位和振幅?也许是指南,我将非常感激。 干杯!

PD。我将附上我使用的FILE,因为:)

EDITED

错误是索引:(

首先,我使用值

定义了向量
amp = np.array([np.sqrt((A[2*k-1])**2 + (A[2*k])**2) for k in range(1,nf+1)])
phs = np.array([math.atan2(A[2*k],A[2*k-1]) for k in range(1,nf+1)])

然后,为了构建信号,我定义了:

def term(t): return np.array([amp[k]*np.sin(k*w*t + phs[k]) for k in range(len(amp))])
Signal = np.array([A0+sum(term(phase[i])) for i in range(len(mag))])

但是在np.sin()中,k应该是k + 1,因为索引从0开始__·

def term(t): return np.array([amp[k]*np.sin((k+1)*w*t + phs[k]) for k in range(len(amp))])
plt.plot(phase,Signal,'r-',lw=3)

enter image description here

就是这样。

感谢Marco Tompitak的帮助!!

1 个答案:

答案 0 :(得分:1)

您为信号指定了错误的时间段:

#period of the signal
per=0.178556

这为您提供了最终的傅立叶拟合,实际上最大周期为~0.17。问题是这个数字指定了傅里叶级数中存在的最长周期。该功能仅具有0.17或更短的组件。显然你期望适合周期〜1,所以它永远不会恰当地接近。您应该指定per=1.0。算法没有错;在Mathematica中快速编写类似算法可以得到相同的输出和合理的结果:

enter image description here