首页 > 解决方案 > 如何使由assign()创建的变量在R包中可见

问题描述

我正在为一个类似于下面的 R 包编写一个函数。该函数data分成k块并lm()在 的子集上运行datacoef然后创建一个名为的数据框,该数据框存储每个输出lm对象的系数,并且coef是函数返回的内容。

func <- function(formula, data, k){
  folds <- cut(seq(1, nrow(data)), breaks=k, labels=FALSE)
  for(i in 1:k){
    tstIdx <- which(folds==i, arr.ind = TRUE)
    trn <- data[-tstIdx, ]
    assign(paste0('lm', i), lm(as.formula(formula), data = trn))
  }

  coefs <- data.frame(lm1=numeric(length(lm1$coefficients)))
  for(i in 1:k){
    coefs[, paste0('lm', i)] <- get(paste0('lm', i))$coefficients
  }

  return(coefs)
}

#Test func
library(datasets)
data(mtcars)
mtcars_coefs <- func('mpg~.', mtcars, 5)
print(mtcars_coefs)
            lm1          lm2         lm3          lm4           lm5
1  18.930505234 -11.52502902 15.33671764 34.344163557 -1.423949e+01
2  -0.026451367  -0.62542095  0.19530279 -0.983487140  1.019901e+00
3   0.006726114   0.03824514  0.01586916  0.003882512  6.283603e-05
4  -0.026141009  -0.01646497 -0.02470510 -0.010100503 -8.608105e-03
5  -0.430795818   1.04213865 -0.05029561  0.707478977  5.183456e+00
6  -2.811187445  -6.43034312 -5.97395758 -3.264676799 -5.520332e-01
7   0.684446470   2.24100765  0.96305888  0.102627465  5.468843e-01
8   1.033639000  -1.35217769 -0.14155710 -0.247260138 -1.086643e-01
9   4.674891158   2.52237260  0.37723390  0.089823364  2.841110e+00
10  0.201546058   1.10453631  1.24816558 -0.104956417  2.342505e+00
11 -0.257196875   0.49039883  0.17770208 -0.324387269 -2.453959e+00

我创建和添加系数的方式是使用创建的第一个对象coef对其进行初始化。lm这工作正常,但是当我对包运行检查时,我收到以下错误:

* checking R code for possible problems ... [7s] NOTE
func: no visible binding for global variable 'lm1'
Undefined global functions or variables:
  lm1

如何编辑代码以使其lm1“可见”,或者如何告诉包检查忽略该问题?

标签: rr-package

解决方案


这是一种重写函数以仅使用列表的方法。

func <- function(formula, data, k){
  folds <- cut(seq(1, nrow(data)), breaks=k, labels=FALSE)
  foldlist <- unique(folds)
  models <- lapply(foldlist, function(i) {
    tstIdx <- which(folds==i, arr.ind = TRUE)
    trn <- data[-tstIdx, ]
    lm(as.formula(formula), data = trn)
  })
  names(models) <- paste0("lm", foldlist)

  as.data.frame(sapply(models, function(m) {
    coef(m)
  }))
}

mtcars_coefs <- func('mpg~.', mtcars, 5)

在 R 中,你只是sapply/lapply在集合。无需创建命名变量,只需命名列表的元素。


推荐阅读