12

実験データから曲線をプロットする方法を探しています。データは、勾配が浅い小さな線形レジームと、しきい値の後に急な線形レジームが続くことを示しています。

私のデータはここにあります: http://pastebin.com/H4NSbxqr
ここにプロットされています

2 本の線でデータを比較的簡単に適合させることができますが、理想的には連続した線で適合させたいと考えています。これは、しきい値の周りで滑らかな曲線が結合された 2 本の線のように見えるはずです (上記のデータでは約 5000)。

scipy.optimize curve_fit直線と指数関数の合計を含む関数を使用して試してみました。

y = a*x + b + c*np.exp((x-d)/e)

何度も試みたにもかかわらず、解決策は見つかりませんでした。

適切な配布/方法の選択または実装のいずれかについて、誰かが何か提案があれば、大curve_fit歓迎です。

4

5 に答える 5

4

@ user423805 の回答を使用しました (Google グループのスレッド経由で見つかりました: https://groups.google.com/forum/#!topic/lmfit-py/7I2zv2WwFLU ) が、3 つ以上のセグメントを使用しようとするといくつかの制限があることに気付きました.

np.maximumミニマイザーエラー関数を適用したり(b1 + b2)、@ user423805 の回答を追加したりする代わりに、ミニマイザーと最終用途の両方に同じ線形スプライン計算を使用しました。

# least_splines_calc works like this for an example with three segments    
# (four threshold params, three gamma params):
#
# for      0 < x < gamma0 : y = th0 + (th1 * x) 
# for gamma0 < x < gamma1 : y = th0 + (th1 * x) + (th2 * (x - gamma0)) 
# for gamma1 < x          : y = th0 + (th1 * x) + (th2 * (x - gamma0)) + (th3 * (x - gamma1))  
#

def least_splines_calc(x, thresholds, gammas):

    if(len(thresholds) < 2):
        print("Error: expected at least two thresholds")
        return None

    applicable_gammas = filter(lambda gamma: x > gamma , gammas)

    #base result  
    y = thresholds[0] + (thresholds[1] * x)

    #additional factors calculated depending on x value
    for i in range(0, len(applicable_gammas)):
        y = y + ( thresholds[i + 2] * ( x - applicable_gammas[i] ) )

    return y

def least_splines_calc_array(x_array, thresholds, gammas):
    y_array = map(lambda x: least_splines_calc(x, thresholds, gammas), x_array)
    return y_array

def err(params, x, data):

    th0 = params['th0'].value
    th1 = params['th1'].value
    th2 = params['th2'].value
    th3 = params['th3'].value
    gamma1 = params['gamma1'].value
    gamma2 = params['gamma2'].value

    thresholds = np.array([th0, th1, th2, th3])
    gammas = np.array([gamma1, gamma2])


    fit = least_splines_calc_array(x, thresholds, gammas)

    return np.array(fit)-np.array(data)

p = lmfit.Parameters()
p.add_many(('th0', 0.), ('th1', 0.0),('th2', 0.0),('th3', 0.0),('gamma1', 9.),('gamma2', 9.3)) #NOTE: the 9. / 9.3 were guesses specific to my data, you will need to change these

mi = lmfit.minimize(err_alt, p, args=(np.array(dfseg.Temp), np.array(dfseg.C)))

最小化後、最小化によって検出されたパラメータをしきい値とガンマの配列に変換して、linear_splines_calc を再利用して線形スプライン回帰をプロットします。

参照: 最小スプラインを説明するさまざまな場所がありますが (@ user423805はhttp://www.statpower.net/Content/313/Lecture%20Notes/Splines.pdfを使用したと思います。(b1 + b2)同様の方程式)、私にとって最も意味のあるものはこれでした (Rob Schapire / Zia Khan at Princeton): https://www.cs.princeton.edu/courses/archive/spring07/cos424/scribe_notes/0403 .pdf - セクション 2.2 は線形スプラインに入ります。以下抜粋:

ここに画像の説明を入力

ここに画像の説明を入力

ここに画像の説明を入力

于 2015-12-20T23:12:48.807 に答える