R中的rmse函数问题

Posted

技术标签:

【中文标题】R中的rmse函数问题【英文标题】:rmse function issue in R 【发布时间】:2020-09-07 14:33:26 【问题描述】:

我有一个 R 代码,其中包含一些嵌套括号 for 循环,我在其中使用了 Metrics 包中的 rmse() 函数。我在没有该功能的情况下尝试了它并且它有效,但在我的嵌套 R 代码中它没有。

这就是我想用R做的事情

    我已生成 50 个时间序列数据集。 我将同一时间序列数据集分割成以下大小的块:2,3,...,48,49 让我从上面的步骤 1 中形成了 48 个不同的时间序列。 我将每个 48 时间序列数据集划分为 traintest 集,因此我可以使用 Metrics 包中的 rmse 函数来获取步骤中形成的 48 个子序列的均方根误差 (RMSE) 2. 每个系列的 RMSE 然后根据它们的块大小制成表格 我为每个 48 个不同的时间序列数据集获得了最好的 ARIMA 模型。

我的 R 代码

 # simulate arima(1,0,0)
 library(forecast)
 library(Metrics)
 n <- 50
 phi <- 0.5
 set.seed(1)
 wn <- rnorm(n, mean=0, sd=1)
    ar1 <- sqrt((wn[1])^2/(1-phi^2))
 for(i in 2:n)
   ar1[i] <- ar1[i - 1] * phi + wn[i]
 
 ts <- ar1

 t<-length(ts)# the length of the time series
 li <- seq(n-2)+1 # vector of block sizes(i.e to be between 1 and n exclusively)

 RMSEblk<-matrix(nrow = 1, ncol = length(li))#vector to store block means
 colnames(RMSEblk)<-li
 for (b in 1:length(li))
     l<- li[b]# block size
     m <- ceiling(t / l) # number of blocks
     blk<-split(ts, rep(1:m, each=l, length.out = t)) # divides the series into blocks
     singleblock <- vector() #initialize vector to receive result from for loop
     for(i in 1:10)
         res<-sample(blk, replace=T, 100) # resamples the blocks
         res.unlist<-unlist(res, use.names = F) # unlist the bootstrap series
         # Split the series into train and test set
         train <- head(res.unlist, round(length(res.unlist) * 0.6))
         h <- length(res.unlist) - length(train)
         test <- tail(res.unlist, h)

        # Forecast for train set
        model <- auto.arima(train)
        future <- forecast(test, model=model,h=h)
        nfuture <- as.numeric(out$mean) # makes the `future` object a vector
        # use the `rmse` function from `Metrics` package
        RMSE <- rmse(test, nn)
        singleblock[i] <- RMSE # Assign RMSE value to final result vector element i
    
    #singleblock
    RMSEblk[b]<-mean(singleblock) #store into matrix
 
 RMSEblk

我遇到的错误

#Error in rmse(test, nn): unused argument (nn)
#Traceback:

但是当我写的时候

library(forecast)

train <- head(ar1, round(length(ar1) * 0.6))
h <- length(ar1) - length(train)
test <- tail(ar1, h)
model <- auto.arima(train)
#forecast <- predict(model, h)
out <- forecast(test, model=model,h=h)
nn <- as.numeric(out$mean)
rmse(test, nn)

确实有效

请指出我遗漏了什么?

【问题讨论】:

【参考方案1】:

您的代码没有定义 nn。其他有效的代码有 nn。要使用干净的 slate 启动代码,请将此行作为第一个可执行行:

rm(list=ls())

【讨论】:

【参考方案2】:

在您的 for 循环中进行两次非常小的更正后,我能够运行您的代码。请参阅两行注释:

 for (b in 1:length(li))
     l<- li[b]
     m <- ceiling(t / l)
     blk<-split(ts, rep(1:m, each=l, length.out = t))
     singleblock <- vector()
     for(i in 1:10)
         res<-sample(blk, replace=T, 100)
         res.unlist<-unlist(res, use.names = F)
         train <- head(res.unlist, round(length(res.unlist) * 0.6))
         h <- length(res.unlist) - length(train)
         test <- tail(res.unlist, h)

        model <- auto.arima(train)
        future <- forecast(test, model=model,h=h)
        nfuture <- as.numeric(future$mean) # EDITED: `future` instead of `out`
        RMSE <- rmse(test, nfuture) # EDITED: `nfuture` instead of `nn`
        singleblock[i] <- RMSEi
    
    RMSEblk[b]<-mean(singleblock)
 

这些拼写错误可能不会导致错误,因为在您运行 for 循环时,nnout 是在全局环境中定义的。一个好的调试技巧是重新启动 R 并尝试重现问题。

【讨论】:

以上是关于R中的rmse函数问题的主要内容,如果未能解决你的问题,请参考以下文章

如何在使用train()和r中的交叉验证时绘制RMSE与装袋尝试的树数

回归任务中的评价指标之MSE,RMSE,MAE,R-Squared,MAPE

如何找到 RMSE 值?啥是好的 RMSE 值?

R语言使用DALEX包的model_performance函数对h2o包生成的多个算法模型进行残差分布分析并使用箱图进行残差分布的可视化直方图中的大红点为残差的均方根误差RMSE

Keras 中的 RMSE/RMSLE 损失函数

R语言使用yardstick包的rmse函数评估回归模型的性能评估回归模型在每个交叉验证(或者重采样)的每一折fold上的RMSE以及整体的均值RMSE(其他指标maemape等计算方式类似)