如何使用scipy.optimize.least_squares获得鲁棒的非线性回归拟合?

时间:2018-10-22 13:18:18

标签: python scipy least-squares non-linear-regression robust

我的具体问题是我似乎无法将我的数据转换为浮点数。我有数据,只是想使用我的模型方程拟合一条稳健的曲线:

  

y = a * e ^(-b * z)

这本菜谱是我的参考书:click

以下是我的尝试。我得到这个:

  

TypeError:“无法理解数据类型”

我相信这是因为我的列是字符串,所以我尝试了pd.Series.astype()

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from scipy.optimize import least_squares

for i in range(1):

    def model(z, a, b):
        y = a * np.exp(-b * z)
        return y
    data = pd.read_excel('{}.xlsx'.format(600+i), names = ['EdGnd','380','395','412','443','465','490','510','520','532','555','560','565','589','625','665','670','683','694','710','Temp','z','EdZTemp','Tilt','Roll','EdZVin'])
    data.dropna(axis = 0, how = 'any')
    data.astype('float')
    np.dtype(data)
    data.plot.scatter('z','380') 
    def fun(x, z, y):
        return x[0] * np.exp(-x[1] * z) - y
    x0 = np.ones(3)
    rbst1 = least_squares(fun, x0, loss='soft_l1', f_scale=0.1, args=('z', 'ed380'))
    y_robust = model('z', *rbst1.x)
    plt.plot('z', y_robust, label='robust lsq')
    plt.xlabel('$z$')
    plt.ylabel('$Ed$')
    plt.legend();

1 个答案:

答案 0 :(得分:1)

我认为问题在于您在apply plugin: 'com.android.application' android { compileSdkVersion 28 buildToolsVersion '28.0.3' final def config = defaultConfig { applicationId "com.suddenlink.suddenlink2go.uat" minSdkVersion 14 targetSdkVersion 28 versionCode 20200 versionName "2.2.0-RC" } config buildTypes { release { signingConfig null } } compileOptions { sourceCompatibility JavaVersion.VERSION_1_7 targetCompatibility JavaVersion.VERSION_1_7 } lintOptions { checkReleaseBuilds false // Or, if you prefer, you can continue to check for errors in release builds, // but continue the build even when errors are found: abortOnError false } packagingOptions { exclude 'META-INF/DEPENDENCIES' exclude 'META-INF/LICENSE' exclude 'META-INF/LICENSE.txt' exclude 'META-INF/license.txt' exclude 'META-INF/NOTICE' exclude 'META-INF/NOTICE.txt' exclude 'META-INF/notice.txt' exclude 'META-INF/ASL2.0' } useLibrary 'org.apache.http.legacy' } dependencies { implementation(project(':androidpdfview')) { exclude group: 'com.android.support', module: 'support-v4' } implementation fileTree(include: ['*.jar'], dir: 'libs') implementation project(':anvatoandroidsdkcore') implementation 'com.android.support:appcompat-v7:21.0.3' implementation 'com.google.android.gms:play-services:6.5.87' implementation 'com.android.volley:volley:1.1.1' implementation 'com.google.code.gson:gson:2.8.2' implementation files('libs/commons-logging-1.1.2.jar') } 中传递了'z',这是一个字符串,因此不能在乘法中使用。

下面是一些使用curve_fit的代码,该代码使用了args,但使用起来可能会更容易一些:

least_squares

这将绘图

enter image description here

您可以尝试根据需要调整此代码。

如果要使用import matplotlib.pyplot as plt import numpy as np from scipy.optimize import curve_fit # your model definition def model(z, a, b): return a * np.exp(-b * z) # your input data x = np.array([20, 30, 40, 50, 60]) y = np.array([5.4, 4.0, 3.0, 2.2, 1.6]) # do the fit with some initial values popt, pcov = curve_fit(model, x, y, p0=(5, 0.1)) # prepare some data for a plot xx = np.linspace(20, 60, 1000) yy = model(xx, *popt) plt.plot(x, y, 'o', xx, yy) plt.title('Exponential Fit') plt.show() ,可以使用:

f_scale

请参见documentation

  

小矮人

     

将关键字参数传递给method ='lm'或minimum_squares的minimumsq。

如果您遇到未解决的问题,则默认使用popt, pcov = curve_fit(model, x, y, p0=(5, 0.1), method='trf', f_scale=0.1) ,它使用method='lm'而不接受leastsq作为关键字。因此,我们可以使用f_scale,然后使用method='trf'接受least_squares