glm `Foregnet()` Ошибка: нет применимого метода для "предиката" применяется к объекту класса "список"
У меня проблема с управлением типами объектов, поступающими в функцию предсказания. Вот моя упрощенная функция, которая генерирует glm
объект.
fitOneSample <- function(x,data,sampleSet)
{
#how big of a set are we going to analyze? Pick a number between 5,000 & 30,000, then select that many rows to study
sampleIndices <- 1:5000
#now randomly pick which columns to study
colIndices <- 1:10
xnames <- paste(names(data[,colIndices]),sep = "")
formula <- as.formula(paste("target ~ ", paste(xnames,collapse = "+")))
glm(formula,family=binomial(link=logit),data[sampleIndices,])
}
myFit <- fitOneSample(1,data,sampleSet)
fits <- sapply(1:2,fitOneSample,data,sampleSet)
all.equal(myFit,fits[,1]) #different object types
#this works
probability <- predict(myFit,newdata = data)
#this doesn't
probability2 <- predict(fits[,1],newdata = data)
# Error in UseMethod("predict") :
# no applicable method for 'predict' applied to an object of class "list"
Как получить доступ к столбцу в fits[,1]
так что я могу использовать функцию предсказания, чтобы получить тот же результат, что я сделал с myFit
?
1 ответ
Я думаю, что теперь я могу восстановить вашу ситуацию.
fits <- sapply(names(trees),
function (y) do.call(lm, list(formula = paste0(y, " ~ ."), data = trees)))
Это использует встроенный набор данных trees
В качестве примера можно привести три линейные модели:
Girth ~ Height + Volume
Height ~ Girth + Volume
Volume ~ Height + Girth
Так как мы использовали sapply
и каждая итерация возвращает одно и то же lm
объект, или список длиной 12, результаты будут упрощены до 12 * 3
матрица:
class(fits)
# "matrix"
dim(fits)
# 12 3
Матричная индексация fits[, 1]
является действительным.
Если вы проверите str(fits[, 1])
, это выглядит почти нормально lm
объект. Но если вы еще проверите:
class(fits[, 1])
# "list"
Эм? У него нет класса "лм"! В следствии, S3
метод диспетчеризации завершится неудачно при вызове универсальной функции predict
:
predict(x)
#Error in UseMethod("predict") :
# no applicable method for 'predict' applied to an object of class "list"
Это можно рассматривать как хороший пример того, что sapply
разрушительно Мы хотим lapply
, или по крайней мере, sapply(..., simplify = FALSE)
:
fits <- lapply(names(trees),
function (y) do.call(lm, list(formula = paste0(y, " ~ ."), data = trees)))
Результат lapply
легче понять. Это список длиной 3, где каждый элемент является lm
объект. Мы можем получить доступ к первой модели через fits[[1]]
, Теперь все будет работать
class(fits[[1]])
# "lm"
predict(fits[[1]])
# 1 2 3 4 5 6 7 8
# 9.642878 9.870295 9.941744 10.742507 10.801587 10.886282 10.859264 10.957380
# 9 10 11 12 13 14 15 16
#11.588754 11.289186 11.946525 11.458400 11.536472 11.835338 11.133042 11.783583
# 17 18 19 20 21 22 23 24
#13.547349 12.252715 12.603162 12.765403 14.002360 13.364889 14.535617 15.016944
# 25 26 27 28 29 30 31
#15.628799 17.945166 17.958236 18.556671 17.229448 17.131858 21.888147
Вы можете исправить свой код по
fits <- lapply(1:2,fitOneSample,data,sampleSet)
probability2 <-predict(fits[[1]],newdata = data)