我使用scipy.optimize.curve_fit
检查数据上的模型
通常,我会有一个多变量函数,这里y_数据是x_数据中两个变量的函数:
import numpy as np
from scipy.optimize import curve_fit
x_data = np.array( [np.arange(10), np.arange(10)*-1+5] )
print( x_data )
[[ 0 1 2 3 4 5 6 7 8 9]
[ 5 4 3 2 1 0 -1 -2 -3 -4]]
y_data = np.arange(10) - 5
print( y_data )
[-5 -4 -3 -2 -1 0 1 2 3 4]
为了适应函数,我只需定义它,并使用curve_fit
:
def lincomb( X, a, b ):
x1 = X[0]
x2 = X[1]
return a*x1*x2 + b
popt, pcov = curve_fit( lincomb, x_data, y_data )
print( popt )
[-0.17857143 -1.57142857]
后者是函数中系数a和b的优化值
现在,我想使用来自sklearn
的交叉验证来进行同样的拟合。为此,我将我的函数打包成一个类,用作估算器,如下所示:
from sklearn.model_selection import cross_validate
class LinComb:
def __init__( self, a=None, b=None ):
self.a = a
self.b = b
def _lincomb_background(self, X, a, b):
x1 = X[0]
x2 = X[1]
return a*x1*x2 + b
def predict( self, X ):
return self._lincomb_background( X, self.a, self.b )
def fit( self, X, y ):
from scipy.optimize import curve_fit
popt, pcov = curve_fit( self._lincomb_background, X, y )
self.a = popt[0]
self.b = popt[1]
return self
def get_params( self, deep=False ):
return { 'a':self.a, 'b':self.b }
def set_params( self, **parameters ):
for parameter, value in parameters.intems():
setattr( self, parameter, value )
return self
然后调用交叉验证时,我在维度中得到一个错误:
cross_validate( LinComb(), x_data, y_data, cv=5, scoring='neg_mean_squared_error' )
---------------------------------------------------------------------------
ValueError Traceback (most recent call last)
<ipython-input-60-e0ff8bb83213> in <module>
----> 1 cross_validate( LinComb(), x_data, y_data, cv=5, scoring='neg_mean_squared_error' )
/usr/local/lib/python3.7/dist-packages/sklearn/model_selection/_validation.py in cross_validate(estimator, X, y, groups, scoring, cv, n_jobs, verbose, fit_params, pre_dispatch, return_train_score, return_estimator, error_score)
215
216 """
--> 217 X, y, groups = indexable(X, y, groups)
218
219 cv = check_cv(cv, y, classifier=is_classifier(estimator))
/usr/local/lib/python3.7/dist-packages/sklearn/utils/validation.py in indexable(*iterables)
228 else:
229 result.append(np.array(X))
--> 230 check_consistent_length(*result)
231 return result
232
/usr/local/lib/python3.7/dist-packages/sklearn/utils/validation.py in check_consistent_length(*arrays)
203 if len(uniques) > 1:
204 raise ValueError("Found input variables with inconsistent numbers of"
--> 205 " samples: %r" % [int(l) for l in lengths])
206
207
ValueError: Found input variables with inconsistent numbers of samples: [2, 10]
事实上,x_数据和y_数据的维度是:
print( x_data.shape, y_data.shape )
(2, 10) (10,)
我仍然不明白为什么维度在第一个简单的情况下工作,以及如何干净地实现这一点
我错过什么了吗
我发现我在尺寸上有两个错误。因为它们是同时发生的,所以我无法轻易地追溯它们。我会把答案贴在这里,也许以后会有用
1。从文档中
修改documentation中的示例有助于追溯维度错误
注意
cross_validation
需要第一个维度相同:注意,对于这些新维度,调用
curve_fit
的简单方法会抛出一个错误:这可以通过在对
curve_fit
的调用中再次转置来解决:2。班级
在
x_data
中使用cross_validation
的新维度(使用问题中定义的类)会引发不同的错误:3。类内部的维度错误
此错误来自
curve_fit
,而不是cross_validation
,并且必须在类内部,在调用模型_lincomb_background()
的^{函数和predict()
中更正。修改后的类为:通过这两个修改后的调用,
cross_validation
按预期工作:4。摘要
a)首先检查
cross_validation()
的尺寸是否正确b)然后在调用
curve_fit()
时调整类内的维度c)最后调整类内的维度,在
predict()
相关问题 更多 >
编程相关推荐