predic.lm 当我使用矩阵变量拟合和预测模型时给出错误数量的预测值
predic.lm gives wrong number of predicted values when I fit and predict a model using a matrix variable
过去,我使用 lm
函数处理 matrix
类型的数据和 data.frame
类型的数据。但我想这是我第一次尝试使用 predict
使用未安装 data.frame
的模型。而且我不知道如何让它发挥作用。
我读了一些其他问题(例如 Getting Warning: " 'newdata' had 1 row but variables found have 32 rows" on predict.lm),我很确定我的问题与拟合模型后得到的系数名称有关。出于某种原因,系数名称是矩阵名称与列名称的粘贴...我一直无法找到解决方法...
library(tidyverse)
library(MASS)
set.seed(1)
label <- sample(c(T,F), nrow(Boston), replace = T, prob = c(.6,.4))
x.train <- Boston %>% dplyr::filter(., label) %>%
dplyr::select(-medv) %>% as.matrix()
y.train <- Boston %>% dplyr::filter(., label) %>%
dplyr::select(medv) %>% as.matrix()
x.test <- Boston %>% dplyr::filter(., !label) %>%
dplyr::select(-medv) %>% as.matrix()
y.test <- Boston %>% dplyr::filter(., !label) %>%
dplyr::select(medv) %>% as.matrix()
fit_lm <- lm(y.train ~ x.train)
fit_lm2 <- lm(medv ~ ., data = Boston, subset = label)
predict(object = fit_lm, newdata = x.test %>% as.data.frame()) %>% length()
predict(object = fit_lm2, newdata = x.test %>% as.data.frame()) %>% length()
# they get different numbers of predicted data
# the first one gets a number a results consistent with x.train
欢迎任何帮助。
我无法修复你的 tidyverse
代码,因为我不使用这个包。但我能够解释为什么 predict
在第一种情况下失败。
让我使用内置数据集 trees
进行演示:
head(trees, 2)
# Girth Height Volume
#1 8.3 70 10.3
#2 8.6 65 10.3
lm
的正常使用方法是
fit <- lm(Girth ~ ., trees)
变量名称(在 ~
的 RHS 上)是
attr(terms(fit), "term.labels")
#[1] "Height" "Volume"
使用predict
时需要在newdata
中提供这些变量。
predict(fit, newdata = data.frame(Height = 1, Volume = 2))
# 1
#11.16125
现在,如果您使用矩阵拟合模型:
X <- as.matrix(trees[2:3])
y <- trees[[1]]
fit2 <- lm(y ~ X)
attr(terms(fit2), "term.labels")
#[1] "X"
您需要在 newdata
中为 predict
提供的变量现在是 X
,而不是 Height
或 Girth
。请注意,由于 X
是矩阵变量,因此在将其馈送到数据框时需要使用 I()
对其进行保护。
newdat <- data.frame(X = I(cbind(1, 2)))
str(newdat)
#'data.frame': 1 obs. of 1 variable:
# $ X: AsIs [1, 1:2] 1 2
predict(fit2, newdat)
# 1
#11.16125
cbind(1, 2)
没有列名也没关系。重要的是这个矩阵在newdat
.
中被命名为X
过去,我使用 lm
函数处理 matrix
类型的数据和 data.frame
类型的数据。但我想这是我第一次尝试使用 predict
使用未安装 data.frame
的模型。而且我不知道如何让它发挥作用。
我读了一些其他问题(例如 Getting Warning: " 'newdata' had 1 row but variables found have 32 rows" on predict.lm),我很确定我的问题与拟合模型后得到的系数名称有关。出于某种原因,系数名称是矩阵名称与列名称的粘贴...我一直无法找到解决方法...
library(tidyverse)
library(MASS)
set.seed(1)
label <- sample(c(T,F), nrow(Boston), replace = T, prob = c(.6,.4))
x.train <- Boston %>% dplyr::filter(., label) %>%
dplyr::select(-medv) %>% as.matrix()
y.train <- Boston %>% dplyr::filter(., label) %>%
dplyr::select(medv) %>% as.matrix()
x.test <- Boston %>% dplyr::filter(., !label) %>%
dplyr::select(-medv) %>% as.matrix()
y.test <- Boston %>% dplyr::filter(., !label) %>%
dplyr::select(medv) %>% as.matrix()
fit_lm <- lm(y.train ~ x.train)
fit_lm2 <- lm(medv ~ ., data = Boston, subset = label)
predict(object = fit_lm, newdata = x.test %>% as.data.frame()) %>% length()
predict(object = fit_lm2, newdata = x.test %>% as.data.frame()) %>% length()
# they get different numbers of predicted data
# the first one gets a number a results consistent with x.train
欢迎任何帮助。
我无法修复你的 tidyverse
代码,因为我不使用这个包。但我能够解释为什么 predict
在第一种情况下失败。
让我使用内置数据集 trees
进行演示:
head(trees, 2)
# Girth Height Volume
#1 8.3 70 10.3
#2 8.6 65 10.3
lm
的正常使用方法是
fit <- lm(Girth ~ ., trees)
变量名称(在 ~
的 RHS 上)是
attr(terms(fit), "term.labels")
#[1] "Height" "Volume"
使用predict
时需要在newdata
中提供这些变量。
predict(fit, newdata = data.frame(Height = 1, Volume = 2))
# 1
#11.16125
现在,如果您使用矩阵拟合模型:
X <- as.matrix(trees[2:3])
y <- trees[[1]]
fit2 <- lm(y ~ X)
attr(terms(fit2), "term.labels")
#[1] "X"
您需要在 newdata
中为 predict
提供的变量现在是 X
,而不是 Height
或 Girth
。请注意,由于 X
是矩阵变量,因此在将其馈送到数据框时需要使用 I()
对其进行保护。
newdat <- data.frame(X = I(cbind(1, 2)))
str(newdat)
#'data.frame': 1 obs. of 1 variable:
# $ X: AsIs [1, 1:2] 1 2
predict(fit2, newdat)
# 1
#11.16125
cbind(1, 2)
没有列名也没关系。重要的是这个矩阵在newdat
.
X