0

I am getting the error below with nlsBoot() any idea what is wrong?

Error in apply(tabboot, 1, quantile, c(0.5, 0.025, 0.975)) : 
  dim(X) must have a positive length

set.seed(1)
x = 1:100
y = x^2+rnorm(100,50,500)
plot(x,y)
d = data.frame(x =x, y=y)
mymodel = nls(y~x^b,start= list(b=1),data = d)
mymodel
library(nlstools)
nlsBoot(mymodel, niter = 999)
Zheyuan Li
  • 71,365
  • 17
  • 180
  • 248
user3022875
  • 8,598
  • 26
  • 103
  • 167

1 Answers1

0

Try to define the formula before applying the nls function, like this:

formula <- as.formula(y ~ x^b)
mymodel <-  nls(formula,start= list(b=1),data = d)

added

Well, I've modified the code and now it can handle one parameter fit.

# My suggestion is to erase all the environment first:
rm(list = ls())
# Then we start again:
set.seed(1)
x = 1:100
y = x^2+rnorm(100,50,500)
plot(x,y)
d = data.frame(x =x, y=y)
mymodel = nls(y~x^b,start= list(b=1),data = d)

Here is the function that you have to use:

nlsboot_onepar <- function (nls, niter = 999) 
{
if (!inherits(nls, "nls")) 
stop("Use only with 'nls' objects")
data2 <- eval(nls$data, sys.frame(0))
fitted1 <- fitted(nls)
resid1 <- resid(nls)
var1 <- all.vars(formula(nls)[[2]])
l1 <- lapply(1:niter, function(i) {
data2[, var1] <- fitted1 + sample(scale(resid1, scale = FALSE), 
                                  replace = TRUE)
nls2 <- try(update(nls, start = as.list(coef(nls)), 
                   data = data2), silent = TRUE)
if (inherits(nls2, "nls")) 
  return(list(coef = coef(nls2), rse = summary(nls2)$sigma))
})
if (sum(sapply(l1, is.null)) > niter/2) 
stop(paste("Procedure aborted: the fit only converged in", 
           round(sum(sapply(l1, is.null))/niter), "% during bootstrapping"))
tabboot <- sapply(l1[!sapply(l1, is.null)], function(z) z$coef,simplify = 
FALSE)
tabboot <- as.matrix(t(as.numeric(tabboot)))
rownames(tabboot) <- "b"
rseboot <- sapply(l1[!sapply(l1, is.null)], function(z) z$rse)
recapboot <- t(apply(tabboot, 1, quantile, c(0.5, 0.025, 
                                           0.975)))
colnames(recapboot) <- c("Median", "2.5%", "97.5%")
estiboot <- t(apply(tabboot, 1, function(z) c(mean(z), sd(z))))
colnames(estiboot) <- c("Estimate", "Std. error")
serr <- sum(sapply(l1, is.null))
if (serr > 0) 
warning(paste("The fit did not converge", serr, "times during 
bootstrapping"))
listboot <- list(coefboot = t(tabboot), rse = rseboot, bootCI = recapboot, 
               estiboot = estiboot)
class(listboot) <- "nlsBoot"
return(listboot)
}

And then we use it:

result <- nlsboot_onepar(mymodel, niter = 999)

If you want to plot the parameter distribution, you can do this:

graphics.off()
plot(density(as.vector(result$coefboot)))
# or
hist(as.vector(result$coefboot))

I hope that helps you.

Blasif
  • 31
  • 6
  • when i do that I get an error Error in nlsBoot(mymodel, niter = 999) : Procedure aborted: the fit only converged in 1 % during bootstrapping – user3022875 Aug 20 '18 at 22:13
  • This function doesn't handle formulas with only one parameter (i've checked). You could try to add in your original code another parameter (without the step of first define the formula and then adjust the model), like y~x^b + mu or y~ a*x^b – Blasif Aug 21 '18 at 00:25