我知道有一些类似的问题,但由于他们都没有带我进一步,我决定问我自己的问题。 对不起,如果我的问题的答案已经存在,但我真的找不到它。
我尝试使用curve_fit将f(x)= a * x ** b拟合为相当线性的数据。它编译正确,但结果如下所示:
问题是,我真的不知道自己在做什么,但另一方面,拟合总是更像是一门艺术,而不是科学,而且至少有一位将军bug with scipy.optimize。
我的数据如下:
x值:
[16.8, 2.97, 0.157, 0.0394, 14.000000000000002, 8.03, 0.378, 0.192, 0.0428, 0.029799999999999997, 0.000781, 0.0007890000000000001]
y值:
[14561.766666666666, 7154.7950000000001, 661.53750000000002, 104.51446666666668, 40307.949999999997, 15993.933333333332, 1798.1166666666666, 1015.0476666666667, 194.93800000000002, 136.82833333333332, 9.9531566666666684, 12.073133333333333]
这是我的代码(在that question的最后一个答案中使用了一个非常好的例子):
def func(x,p0,p1): # HERE WE DEFINE A FUNCTION THAT WE THINK WILL FOLLOW THE DATA DISTRIBUTION
return p0*(x**p1)
# Here you give the initial parameters for p0 which Python then iterates over to find the best fit
popt, pcov = curve_fit(func,xvalues,yvalues, p0=(1.0,1.0))#p0=(3107,0.944)) #THESE PARAMETERS ARE USER DEFINED
print(popt) # This contains your two best fit parameters
# Performing sum of squares
p0 = popt[0]
p1 = popt[1]
residuals = yvalues - func(xvalues,p0,p1)
fres = sum(residuals**2)
print 'chi-square'
print(fres) #THIS IS YOUR CHI-SQUARE VALUE!
xaxis = np.linspace(5e-4,20) # we can plot with xdata, but fit will not look good
curve_y = func(xaxis,p0,p1)
起始值来自与gnuplot的拟合,这似乎是合理的,但我需要交叉检查。
这是打印输出(首先拟合p0,p1,然后是卡方):
[ 4.67885857e+03 6.24149549e-01]
chi-square
424707043.407
我想这是一个很难的问题,所以非常感谢提前!
答案 0 :(得分:1)
当拟合curve_fit
优化(数据 - 模型)的总和^ 2 /(错误)^ 2
如果您没有传递错误(正如您在此处所做的那样),curve_fit
会假定所有点的错误均为1。
在这种情况下,当您的数据跨越多个数量级时,具有最大y值的点在目标函数中占主导地位,并导致curve_fit
尝试以牺牲其他值为代价来适应它们。
解决此问题的最佳方法是在yvalues
中包含错误(看起来就像你在你所绘制的情节中有错误条一样!)。您可以将sigma
curve_fit
参数作为$percent = 10;
$price *= (1 + $percent / 100);
传入。
答案 1 :(得分:1)