使用nls将曲线拟合到R中的威布尔分布

时间:2015-10-13 21:28:17

标签: r nls weibull best-fit-curve

我试图将这些数据拟合到weibull分布:

我的xy变量是:

y <- c(1, 1, 1, 4, 7, 20, 7, 14, 19, 15, 18, 3, 4, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1)
x <- c(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24)

情节如下:

enter image description here

我正在寻找这样的事情: fitted plot

我希望将weibull曲线拟合到它。我在R中使用nls函数:

nls(y ~ ((a/b) * ((x/b)^(a-1)) * exp(- (x/b)^a)))

这个函数总是会抛出错误说:

Error in numericDeriv(form[[3L]], names(ind), env) : 
  Missing value or an infinity produced when evaluating the model
In addition: Warning message:
In nls(y ~ ((a/b) * ((x/b)^(a - 1)) * exp(-(x/b)^a))) :
  No starting values specified for some parameters.
Initializing ‘a’, ‘b’ to '1.'.
Consider specifying 'start' or using a selfStart model

首先,我尝试了不同的起始值而没有任何成功。我无法理解如何制作一个好的&#34;猜测起始值。 然后我使用了SSweibull(x, Asym, Drop, lrc, pwr)函数,这是一个selfStart函数。现在SSWeibull函数需要Asym,Drop,lrc和pwr的值,我不知道这些值可能是什么。

如果有人能帮助我弄清楚如何继续,我将不胜感激。

数据背景:我从bugzilla和我的&#34; y&#34;中获取了一些数据。变量是特定月份报告的错误数量&#34; x&#34;变量是发布后的月份数。

1 个答案:

答案 0 :(得分:4)

您可以考虑修改公式以更好地适应数据。例如,您可以添加一个截距(因为您的数据平坦线为1而不是0,模型想要这样做)和标量乘数,因为您实际上并未拟合密度。

总是值得花些时间真正考虑哪些参数有意义,因为模型拟合程序通常对初始估计非常敏感。您还可以进行网格搜索,在其中提供可能参数的范围,并尝试使用错误捕获功能使用各种组合拟合模型。 nls2可以选择为您执行此操作。

所以,例如,

## Put the data in a data.frame
dat <- data.frame(x=x, y=y)

## Try some possible parameter combinations
library(nls2)
pars <- expand.grid(a=seq(0.1, 100, len=10),
                    b=seq(0.1, 100, len=10),
                    c=1,
                    d=seq(10, 100, len=10))

## brute-force them
## note the model has changed slightly
res <- nls2(y ~ d*((a/b) * ((x/b)^(a-1)) * exp(- (x/b)^a)) + c, data=dat,
           start=pars, algorithm='brute-force')

## use the results with another algorithm
res1 <- nls(y ~ d*((a/b) * ((x/b)^(a-1)) * exp(- (x/b)^a)) + c, data=dat,
           start=as.list(coef(res)))

## See how it looks
plot(dat, col="steelblue", pch=16)
points(dat$x, predict(res), col="salmon", type="l", lwd=2)

enter image description here

不完美,但这只是一个开始。