Я пытаюсь использовать sklearn cross_val_score(). Ниже приведен пример, который я пробовал:
# loocv evaluate random forest on the housing dataset
from numpy import mean
from numpy import std
from numpy import absolute
from pandas import read_csv
from sklearn.model_selection import LeaveOneOut
from sklearn.model_selection import cross_val_score
from sklearn.ensemble import RandomForestRegressor
# load dataset
url = 'https://raw.githubusercontent.com/jbrownlee/Datasets/master/housing.csv'
dataframe = read_csv(url, header=None)
data = dataframe.values
# split into inputs and outputs
X, y = data[:, :-1], data[:, -1]
print(X.shape, y.shape)
# create loocv procedure
cv = LeaveOneOut()
# create model
model = RandomForestRegressor(random_state=1)
# evaluate model
scores = cross_val_score(model, X, y, scoring='neg_mean_absolute_error', cv=cv, n_jobs=-1)
# force positive
scores = absolute(scores)
# report performance
print('MAE: %.3f (%.3f)' % (mean(scores), std(scores)))
Приведенный выше код отлично работает без каких-либо проблем. Но когда я меняю scoring
на r2
, все значения в scores
станут nan
.
Проблема заключается в использовании LeaveOneOut()
в сочетании с r2
в качестве функции подсчета очков. LeaveOneOut() разделит данные таким образом, что только один образец будет использоваться для тестирования, а оставшийся — для обучения. И здесь возникает проблема, когда вы вычисляете r2 на проверочном наборе, используя эту формулу:
знаменатель становится равным нулю, поскольку n=1
(только один образец для проверки), поэтому y_bar = y_i
, поскольку среднее значение равно одному числу, которое у вас есть, это приводит к nan
, которое вы наблюдаете. Это обязательно произойдет, если ваш cv = No. of data points
, как показано ниже:
# evaluate model
scores = cross_val_score(model, X[0:10], y[0:10], scoring='r2', cv=10, n_jobs=-1)
# force positive
scores = absolute(scores)
# report performance
print('MAE: %.3f (%.3f)' % (mean(scores), std(scores)))
MAE: nan (nan)
И теперь, когда я устанавливаю другое значение для n
, все работает нормально:
# evaluate model
scores = cross_val_score(model, X[0:10], y[0:10], scoring='r2', cv=3, n_jobs=-1)
# force positive
scores = absolute(scores)
# report performance
print('MAE: %.3f (%.3f)' % (mean(scores), std(scores)))
MAE: 0.662 (0.229)