import numpy as np
from astropy import modeling
import matplotlib.pyplot as plt
from scipy import optimize
def gaussian(x, amplitude, mean, stddev):
return amplitude * np.exp(-((x - mean)/4/stddev)**2)
# the data
m = modeling.models.Gaussian1D(amplitude=10, mean=100, stddev=10)
x = np.linspace(0, 400, 400)
data = m(x)
# fitting
popt, _ = optimize.curve_fit(gaussian, x, data)
plt.figure(0)
plt.plot(x, data)
plt.plot(x, gaussian(x, *popt))
plt.show()
我运行此命令进行正态分布拟合。但这给了我一个电话。不知道为什么。
但是,如果我将均值降低到45以下,则将非常适合。这是scipy包的设计缺陷吗?
当您使用scipy.optimize.curve_fit时,模型参数的初始估计值(在这种情况下,是幅度,均值和标准偏差)会有很大的不同。您没有提供任何初始猜测。提供猜测值(带有实际值),则拟合为完美(因为高斯是理想的高斯且不添加噪声):
import numpy as np
from astropy import modeling
import matplotlib.pyplot as plt
from scipy import optimize
def gaussian(x, amplitude, mean, stddev):
return amplitude * np.exp(-((x - mean)/4/stddev)**2)
# the data
m = modeling.models.Gaussian1D(amplitude=10, mean=100, stddev=10)
x = np.linspace(0, 400, 400)
data = m(x)
# fitting
popt, _ = optimize.curve_fit(gaussian, x, data, p0 = [10, 100, 10])
plt.figure(0)
plt.plot(x, data)
plt.plot(x, gaussian(x, *popt))
plt.show()
您得到:gaussian fit
您可以通过向数据中添加一些噪声来确保拟合工作,例如:
from astropy import modeling
import matplotlib.pyplot as plt
from scipy import optimize
import numpy as np
def gaussian(x, amplitude, mean, stddev):
return amplitude * np.exp(-((x - mean)/4/stddev)**2)
# the data
m = modeling.models.Gaussian1D(amplitude=10, mean=100, stddev=10)
x = np.linspace(0, 400, 400)
data = m(x)
noise = np.random.normal(len(m))
data = data + noise
# fitting
popt, _ = optimize.curve_fit(gaussian, x, data, p0 = [10, 100, 10])
plt.figure(0)
plt.plot(x, data, 'o', label = 'data')
plt.plot(x, gaussian(x, *popt), label = 'fit')
plt.legend()
plt.show()