Katharina
Katharina

Reputation: 65

predict newdata with NA for smooth.splines

I am doing a smooth.spline() fit and afterwards a prediction with the fit. I have the problem that my newdata has some NAs. Now I'm trying to get NAs for the prediction too. But I don't get it to work.

I have made up some reproducible code to illustrate my problem. I want my newdata and my prediction to be of the same length. I did not have this problem for example when using predict with a loess model. It automatically puts NA to y if x is NA. I saw this question for the prediction of other models (lm, glm,..) but the answers there by setting na.action=na.exclude does not work for me.

x <- c(1:5, NA, 7:12, NA, 15:19, 22:23)
y <- rnorm(length(x))
y[which(is.na(x))] <-NA
length(y) #20

x.new <- c(x[1:18],20,21,x[19:20])
length(x.new) #22

spl <- smooth.spline(x=x[!is.na(y)], y=y[!is.na(y)], spar=0.001)
spl.pr <- predict(spl, x=x.new[!is.na(x.new)], na.action=na.exclude)
length(spl.pr$y) #20

My predict command also won't work if I don't exclude NAs right inside the predict E.g. :

> spl.pr <- predict(spl, x=x.new, na.action=na.exclude)
Error in double(n) : vector size cannot be NA

I hope I made my problem understandable. Help will be very much appreciated. Thanks

Upvotes: 3

Views: 1106

Answers (1)

Zheyuan Li
Zheyuan Li

Reputation: 73315

predict behaves differently for different model class. There is no na.action for stats:::predict.smooth.spline and stats:::predict.smooth.spline.fit. So you have to predict at non NA values only.

spl.pr <- rep(NA, length(x.new))
spl.pr[!is.na(x.new)] <- predict(spl, x = x.new[!is.na(x.new)])$y

Note that spl.pr is not a list with $x and $y, but a numerical vector.


Ok I suspected that. I was unsure though because I did not get an error message when using na.action = na.exclude within the command. Your recommended way around it works well, thank you!

@Katharina Haha, you did not get error because there is a ... argument in predict() function. So basically you can pass in whatever unused argument to it. Try this

predict(spl, x = 5, this.answer.is.useful = TRUE)

Have fun!

Upvotes: 3

Related Questions