如果您尝试运行多项式回归,其中x^2
函数中定义了lm()
,则由于奇点而忽略多项式项。但是,如果我们在lm()
之外定义多项式项,则模型正确拟合。
它似乎应该在两种方式下都一样。 为什么我们需要在lm()
函数之外定义多项式项?
x <- round(rnorm(100, mean = 0, sd = 10))
y <- round(x*2.5 + rnorm(100))
# Trying to define x^2 in the model, x^2 is dropped
model_wrong <- lm(y ~ x + x^2)
# Define x^2 as its own object
x2 <- x^2
model_right <- lm(y ~ x + x2)
答案 0 :(得分:4)
lm
除非您告诉它,通常通过将其包装在函数中,否则不知道该术语在公式中的开始和停止位置。对于任意计算,您可以将它们包装在I(...)
中,它告诉函数按原样使用它:
set.seed(47)
x <- round(rnorm(100, mean = 0, sd = 10))
y <- round(x*2.5 + rnorm(100))
lm(y ~ x + I(x^2))
#>
#> Call:
#> lm(formula = y ~ x + I(x^2))
#>
#> Coefficients:
#> (Intercept) x I(x^2)
#> 2.563e-01 2.488e+00 -3.660e-06
实际上,您可以在大多数函数调用中包装x^2
,该函数调用将返回可在模型矩阵中使用的求值向量。在某些情况下,cbind
非常方便,但c
,identity
甚至{...}
都可以使用。 I
是专门建立的。
或者,您可以使用poly
函数为您创建两个项,这对于高次多项式非常有用。默认情况下,它会生成正交多项式,这将使系数看起来不同:
lm(y ~ poly(x, 2))
#>
#> Call:
#> lm(formula = y ~ poly(x, 2))
#>
#> Coefficients:
#> (Intercept) poly(x, 2)1 poly(x, 2)2
#> 1.500000 243.485357 -0.004319
即使他们会评估相同的内容:
new <- data.frame(x = seq(-1, 1, .5))
predict(lm(y ~ x + I(x^2)), new)
#> 1 2 3 4 5
#> -2.2317175 -0.9876930 0.2563297 1.5003505 2.7443695
predict(lm(y ~ poly(x, 2)), new)
#> 1 2 3 4 5
#> -2.2317175 -0.9876930 0.2563297 1.5003505 2.7443695
如果您真的希望系数相同,请添加raw = TRUE
:
lm(y ~ poly(x, 2, raw = TRUE))
#>
#> Call:
#> lm(formula = y ~ poly(x, 2, raw = TRUE))
#>
#> Coefficients:
#> (Intercept) poly(x, 2, raw = TRUE)1 poly(x, 2, raw = TRUE)2
#> 2.563e-01 2.488e+00 -3.660e-06