簡體   English   中英

如何修復python中的“IndexError:元組索引超出范圍”?

[英]How to fix "IndexError: tuple index out of range" in python?

我正在使用sklearn模塊來查找最佳擬合模型和模型參數。 但是,我在下面有一個意外的索引錯誤:

> IndexError                                Traceback (most recent call
> last) <ipython-input-38-ea3f99e30226> in <module>
>      22             s = mean_squared_error(y[ts], best_m.predict(X[ts]))
>      23             cv[i].append(s)
> ---> 24     print(np.mean(cv, 1))
> IndexError: tuple index out of range

我想要做的是找到最合適的回歸量及其參數,但我得到了上述錯誤。 我查看了SO並嘗試了這個解決方案,但仍然出現相同的錯誤。 任何想法來修復這個錯誤? 誰能指出我為什么會發生這個錯誤? 任何想法?

我的代碼

from sklearn.model_selection import KFold
from sklearn.metrics import mean_squared_error
from sklearn.linear_model import LinearRegression, Ridge, Lasso
from xgboost.sklearn import XGBRegressor

from sklearn.datasets import make_regression

models = [SVR(), RandomForestRegressor(), LinearRegression(), Ridge(), Lasso(), XGBRegressor()]
params = [{'C': [0.01, 1]}, {'n_estimators': [10, 20]}]

X, y = make_regression(n_samples=10000, n_features=20)

with warnings.catch_warnings():
    warnings.filterwarnings("ignore")
    cv = [[] for _ in range(len(models))]
    fold = KFold(5,shuffle=False)
    for tr, ts in fold.split(X):
        for i, (model, param) in enumerate(zip(models, params)):
            best_m = GridSearchCV(model, param)
            best_m.fit(X[tr], y[tr])
            s = mean_squared_error(y[ts], best_m.predict(X[ts]))
            cv[i].append(s)
    print(np.mean(cv, 1))

所需的輸出

如果有辦法解決上述錯誤,我希望選擇帶參數的最佳擬合模型,然后將其用於估計。 有什么想法可以改進上述嘗試嗎? 謝謝

當你定義

cv = [[] for _ in range(len(models))]

每個模型都有一個空列表。 但是,在循環中,您enumerate(zip(models, params))只有兩個元素的enumerate(zip(models, params)) ,因為您的params列表有兩個元素(因為list(zip(x,y))長度等於min(len(x),len(y) )。

因此,當您使用np.mean計算平均值時,您會得到一個IndexError因為cv中的某些列表是空的(除了前兩個)。

解決方案:如果您不需要在其余模型上使用GridSearchCV ,您可以使用空字典擴展params列表:

params = [{'C': [0.01, 1]}, {'n_estimators': [10, 20]}, {}, {}, {}, {}]

您問題的根本原因是,當您要求對GridSearchCV的 6 個模型進行評估時,您僅提供了前 2 個模型的參數:

models = [SVR(), RandomForestRegressor(), LinearRegression(), Ridge(), Lasso(), XGBRegressor()]
params = [{'C': [0.01, 1]}, {'n_estimators': [10, 20]}]

此設置中enumerate(zip(models, params))的結果,即:

for i, (model, param) in enumerate(zip(models, params)):
    print((model, param))

(SVR(C=1.0, cache_size=200, coef0=0.0, degree=3, epsilon=0.1, gamma='auto',
  kernel='rbf', max_iter=-1, shrinking=True, tol=0.001, verbose=False), {'C': [0.01, 1]})
(RandomForestRegressor(bootstrap=True, criterion='mse', max_depth=None,
           max_features='auto', max_leaf_nodes=None,
           min_impurity_decrease=0.0, min_impurity_split=None,
           min_samples_leaf=1, min_samples_split=2,
           min_weight_fraction_leaf=0.0, n_estimators=10, n_jobs=1,
           oob_score=False, random_state=None, verbose=0, warm_start=False), {'n_estimators': [10, 20]})

即最后 4 個模型被簡單地忽略,所以你在cv得到它們的空條目:

print(cv)
# result:
[[5950.6018771284835, 5987.293514740653, 6055.368320208183, 6099.316091619069, 6146.478702335218], [3625.3243553665975, 3301.3552182952058, 3404.3321983193728, 3521.5160621260898, 3561.254684271113], [], [], [], []]

這會在嘗試獲取np.mean(cv, 1)時導致下游錯誤。

正如 Psi 在他們的回答中已經正確指出的那樣,解決方案是在您實際上執行任何 CV 搜索的模型中尋找空字典; 省略XGBRegressor (尚未安裝),結果如下:

models = [SVR(), RandomForestRegressor(), LinearRegression(), Ridge(), Lasso()]
params2 = [{'C': [0.01, 1]}, {'n_estimators': [10, 20]}, {}, {}, {}]

cv = [[] for _ in range(len(models))]
fold = KFold(5,shuffle=False)
for tr, ts in fold.split(X):
    for i, (model, param) in enumerate(zip(models, params2)):
        best_m = GridSearchCV(model, param)
        best_m.fit(X[tr], y[tr])
        s = mean_squared_error(y[ts], best_m.predict(X[ts]))
        cv[i].append(s)

其中print(cv)給出:

[[4048.660483326826, 3973.984055352062, 3847.7215568088545, 3907.0566348092684, 3820.0517432992765], [1037.9378737329769, 1025.237441119364, 1016.549294695313, 993.7083268195154, 963.8115632611381], [2.2948917095935095e-26, 1.971022007799432e-26, 4.1583774042712844e-26, 2.0229469068846665e-25, 1.9295075684919642e-26], [0.0003350178681602639, 0.0003297411022124562, 0.00030834076832371557, 0.0003355298330301431, 0.00032049282437794516], [10.372789356303688, 10.137748082073076, 10.136028304131141, 10.499159069700834, 9.80779910439471]]

print(np.mean(cv, 1))工作正常,給出:

[3.91949489e+03 1.00744890e+03 6.11665355e-26 3.25824479e-04
 1.01907048e+01]

因此,在您的情況下,您確實應該將params更改為:

params = [{'C': [0.01, 1]}, {'n_estimators': [10, 20]}, {}, {}, {}, {}]

正如 Psi 已經建議的那樣。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM