#r #machine-learning #r-caret #predict
#r #машинное обучение #r-каретка #прогнозировать
Вопрос:
Я столкнулся с проблемой с функцией predict.train пакета каретки, которая дает мне несколько случайные прогнозы для моих моделей «положительного контроля» (т. Е. Предполагается, Что она дает относительно хорошие прогнозы). Проблема сохранялась в разных алгоритмах («glmnet» и «rf»). Тем не менее, когда я вычисляю прогнозы вручную, используя конечные коэффициенты модели glmnet, прогнозы работают хорошо.
Вот пример того, что я сделал:
Настройка модели:
## Define fitControl object
fitControl = trainControl(method = "cv",
number = 5)
## Define tuneGrid
glmnet.tuneGrid = expand.grid(alpha = seq(from = 0, to = 1, by = 0.2),
lambda = seq(from = 0, to = 1, by = 0.2))
## Run inner CV
glmnet.fit = train(x = train[,x], y = train[,y],
method = "glmnet", metric = "RMSE",
trControl = fitControl,
tuneGrid = glmnet.tuneGrid)
Извлечение прогнозов с использованием функции predict.train и ручное вычисление с использованием наилучших коэффициентов модели:
## Predict in itest set
glmnet.preds = predict(glmnet.fit, newdata = test)
## Compute manual predictions
glmnet.coefs = coef(glmnet.fit$finalModel, s = glmnet.fit$bestTune$lambda)
manual.preds = as.vector(
glmnet.coefs[1,]
glmnet.coefs[2,]*test$t0_bdi_std
glmnet.coefs[3,]*test$sex_std
glmnet.coefs[4,]*test$age_std
glmnet.coefs[5,]*test$BMI_std)
Если я оцениваю прогнозы, я получаю разные значения:
> glmnet.preds
3 6 7 17 20 23 27 37 38 47 54
21.07649 18.32825 18.30302 19.02607 21.18579 21.91725 18.84951 21.46324 18.64773 21.30349 22.01814
56 66 67 69 74 77 88 89 92 98 104
21.52209 21.44642 18.65614 21.18579 19.54734 19.67345 21.86680 20.96719 18.79066 21.03445 20.81586
108
19.19422
> manual.preds
[1] 20.97291 17.80435 17.77912 15.64083 13.21352 17.52165 20.47162 18.85598 22.05817 15.11957 21.91455
[12] 18.55717 16.69316 17.05924 25.01654 27.60745 22.36856 18.54421 16.21393 19.69743 18.06953 18.56627
[23] 23.32000
Я также получаю различия в индексах соответствия и выходных данных predict.train, которые кажутся относительно случайными, в то время как ручное прогнозирование работает так, как ожидалось:
> postResample(test[, y], glmnet.preds)
RMSE Rsquared MAE
13.665491040 0.004892648 11.756136481
> postResample(test[, y], manual.preds)
RMSE Rsquared MAE
11.7743854 0.4606725 10.0398907
Интересное примечание: я попытался создать полностью воспроизводимый пример с моделируемыми данными, но затем predict.train привел к тем же результатам.
Мне было бы очень любопытно (и безмерно благодарно), если кто-нибудь знает, что приводит к этим результатам и как это исправить.
Информация о системе:
- Версия R: 4.0.2
- версия каретки: 6.0-86
Комментарии:
1. Что вы имеете в виду: «Я пытался создать полностью воспроизводимый пример с моделируемыми данными, но затем predict.train привел к тем же результатам». Вы говорите, что смоделированные результаты совпадают с тем, что вы показываете в сообщении, или что вы не видите ту же проблему с результатами последующей выборки с смоделированными данными, что и с вашими реальными данными.
2. Извините за путаницу. Для смоделированных данных прогнозы дают те же результаты с predict.train, что и при ручном вычислении (как и должно быть), поэтому я не могу предоставить полностью воспроизводимый пример ошибки.
Ответ №1:
Поскольку данные не предоставлены, нет способа узнать, верны ли вычисления. Ниже я использую пример набора данных:
library(mlbench)
library(caret)
data(BostonHousing)
#exclude one factor column
tr_dat = BostonHousing[1:300,-4]
test_dat = BostonHousing[301:nrow(BostonHousing),-4]
fitControl = trainControl(method = "cv",number = 5)
glmnet.tuneGrid = expand.grid(alpha = seq(from = 0, to = 1, by = 0.2),
lambda = seq(from = 0, to = 1, by = 0.2))
glmnet.fit = train(x = tr_dat[,-ncol(tr_dat)], y = tr_dat[,ncol(tr_dat)],
method = "glmnet",etric = "RMSE",trControl = fitControl,tuneGrid = glmnet.tuneGrid)
Прогнозирование каретки:
pred_caret = predict(glmnet.fit,newdata=test_dat)
Мы делаем прогноз вручную, поэтому вы можете получить его, выполнив матричное умножение %*%
между вашими коэффициентами и матрицей-предиктором:
predictor = cbind(Intercept=1,as.matrix(test_dat[,-ncol(test_dat)]))
coef_m = as.matrix(coef(glmnet.fit$finalModel,s=glmnet.fit$bestTune$lambda))
pred_manual = predictor %*% coef_m
table(pred_manual == pred_caret)
TRUE
206
Вы получаете обратно точно то же самое
Комментарии:
1. Спасибо за тестирование с такой детализацией. Я бы хотел поделиться данными, чтобы еще больше осветить проблему, но я ограничен из-за конфиденциальности данных. Я также попробовал аналогичный подход, моделируя данные, где я также получаю те же результаты при умножении коэффициентов и функции прогнозирования. Однако по какой-то причине ошибка сохраняется с моими фактическими данными, а также распространяется на другие алгоритмы, где я также не могу протестировать ручное прогнозирование (например, случайные леса)
2. Привет @NilsKappelmann, конечно, данные конфиденциальны. Вы опубликовали вопрос, и здесь это лучшее, что мы можем сделать. Опять же, под умножением вы подразумеваете матричное умножение (как я делал выше) или ручное, которое у вас есть в вашем примере
3. Я надеюсь, что он наткнулся на то, что я благодарен, потому что моя записка о конфиденциальности не предполагала иного (только то, что я разочарован тем, что не поделился более подробной информацией о проблемах, которые у меня есть). Я также не понял, что ваш комментарий о матричном умножении был вопросом (я воспринял это как предложение). До сих пор я использовал ручной подход, упомянутый выше.