我要拟合的信号是多个正弦函数(和噪声)的叠加,我想同时适用于所有频率。这里有一个示例数据文件,由两个频率240d^-1和261.8181d^-1生成: https://owncloud.gwdg.de/index.php/s/JZQTJ3VMYZH8qNB和plot of the time series (excerpt)
到目前为止,我可以拟合一个接一个的正弦函数,同时保持频率固定在一个值上。我从周期图中得到频率,最后我对拟合的振幅和相位感兴趣。在
import numpy as np
from scipy import optimize
import bottleneck as bn
def f_sinus0(x,a,b,c,d):
return a*np.sin(b*x+c)+d
def fit_single(t, flux, flux_err, freq_model, c0 = 0.):
# initial guess for the parameter
d0 = bn.nanmean(flux)
a0 = 3*np.std(flux)/np.sqrt(2.)
# fit function with fixed frequency "freq_model"
popt, pcov = optimize.curve_fit(lambda x, a, c, d:
f_sinus0(x, a, freq_model*2*np.pi, c, d),
t, flux, sigma = flux_err, p0 = (a0,c0,d0),
bounds=([a0-0.5*abs(a0),-np.inf,d0-0.25*abs(d0)],
[a0+0.5*abs(a0),np.inf,d0+0.25*abs(d0)]),
absolute_sigma=True)
perr = np.sqrt(np.diag(pcov))
return popt, perr
filename = 'data-test.csv'
data = np.loadtxt(filename)
time = data[0]
flux = data[1]
flux_err = data[2]
freq_model = 260 #d^-1
popt, perr = fit_single(time, flux, flux_err, freq_model, c0 = 0.)
现在我想同时拟合两个频率。我定义了一个函数,它根据输入参数列表的长度返回拟合函数的和
^{pr2}$进行拟合
def fit_multiple(t, flux, flux_err, guess):
popt, pcov = optimize.curve_fit(
f_multiple_sin, t, flux, sigma=flux_err, p0=guess,
bounds=(guess-np.multiply(guess,0.1),guess+np.multiply(guess,0.1)),
absolute_sigma=True
)
perr = np.sqrt(np.diag(pcov))
return popt, perr
guess = [4.50148944e-03, 2.40000040e+02, 3.01766641e-03, 8.99996136e-01, 3.14546648e-03, 2.61818207e+02, 2.94282247e-03, 5.56770657e-06]
popt, perr = fit_multiple(time, flux, flux_err, guess)
使用单个拟合的结果作为初始参数guess = [amplitude1, frequency1, phase1, offset1, amplitude2,...]
但是我怎样才能拟合出多个正弦函数,每个函数都有一个固定的频率?在这种情况下,lambda
方法对我来说似乎不是那么直接。在
这是一个使用
scipy.optimize.leastsq
的解决方案,它给了我更多的自由。不过,在错误评估时,你必须小心。另一方面,在参数数目方面,它没有curve_fit
那么严格。 在这个解决方案中,我基本上符合三个列表,振幅、频率和相位。At似乎很方便将它按这样的顺序传递给函数。 最后你可以固定任何频率子集。不过,我的印象是,收敛对起始参数非常敏感。在提供:
^{pr2}$相关问题 更多 >
编程相关推荐