我有一个名为defaultPacks
的对象,其中包含我使用的所有计算机上安装的软件包的名称。缩写:
defaultPacks <- c(
"AER",
"plyr",
"dplyr"
)
我想将此对象保存到共享目录中,所有这些文件都可以访问。我正在为此使用Dropbox,当R运行时同步总是暂停。
save(defaultPacks,
file.path("C:","Users","andrewH","Dropbox","R_PROJ","sharedSettings.rdata"))
然后,我想加载对象并安装名称在对象
defaultPacks
中的包。SyncPacks <- function(fileString){
defaultPacks <- load(file=fileString)
install.packages(defaultPacks, repos="http://cran.us.r-project.org")
}
SyncPacks(file.path("C:","Users","andrewH","Dropbox","R_PROJ","sharedSettings.rdata")
如果执行此操作,则会收到警告:
Warning in install.packages: package ‘defaultPacks’ is not available (for R version 3.2.1)
加载并分配它后,我立即查看
defaultPacks
中的内容:字符串"defaultPacks"
。因此,似乎加载只是一个字符串而不是一个对象。所以我回到我的保存,然后尝试
save(get(defaultPacks), file.path(etc.))
这给了我一个不同的错误:
Error in save(get("defaultPacks"), file = file.path("C:", "Users", "andrewH", :
object ‘get("defaultPacks")’ not found.
然后,我尝试了
dynGet()
,结果相同。因此,在将符号视为字符串之前,现在将函数视为字符串。
因此,我尝试使用list选项进行保存:
save(list = defaultPacks, file = file.path(etc))
并得到另一个错误:
Error in save(list = defaultPacks, file = file.path("C:", "Users", "andrewH", :
objects ‘AER’, ‘plyr’, ‘dplyr’, (etc.) not found
因此,在无法到达字符 vector 的地方,现在我要进行射击,评估
defaultPacks
以查找字符串,然后将每个字符串视为符号,并将其评估为(不存在的)对象。所以,我想知道如何使这项工作。但是我要的不只是这些。我一直都有这个问题,或者类似的问题。使用R数年后,我仍然每周有几次。我不知道在任何给定的场合R将要执行多少步骤。我给函数提供了一个对象名,该函数将其视为字符串。我将一个函数传递给一个字符串,然后R函数将其转换为符号并尝试对其进行求值。在这里,我不明白为什么
save
函数不保存我给它的对象,然后用load
退还给它。我已经阅读了十本不同的R书中有关范围界定的讨论,从钱伯斯的“数据分析软件”到威克姆的“高级R”。两次。在某些情况下四次。我知道一个函数的四个环境,以及调用堆栈和环境父链之间的区别。但是,很明显,我缺少一些基本知识。不仅仅是我不知道为什么
save
在...
参数中没有使用名称并将其保存为对象(除非问题在加载端)。我不知道该怎么办该函数描述在...
中说:“要保存的对象的名称(作为符号或字符串)。”那么为什么将名称另存为字符串呢?还是为什么加载返回一个字符串,如果保存保存了一个对象?我怎么能预测呢?经验丰富的R程序员,我知道您可以提前告诉给定的R函数如何处理其参数之一。您知道将对其进行评估的程度。您可以将其移动到所需位置,然后停止。您不必每次想弄清楚
str()
认为其参数的含义时就将ojit_code写入函数。你怎么做呢?血腥的“R hell ”。这是的轻描淡写。
最佳答案
解决此问题的一种方法是注意defaultPacks
的值从这些操作之前更改为之后。
> fname = tempfile()
> orig = defaultPacks = c("AER", "plyr", "dplyr")
> save(defaultPacks, file=fname)
> defaultPacks = load(fname)
> identical(orig, defaultPacks)
[1] FALSE
问题始于对
save()
的作用的理解。在?save
中,保存的对象名为defaultPacks
,其值为c("AER", "plyr", "dplyr")
。 save()
可以保存多个对象,每个对象都有一个名称和关联的值,因此它必须以某种方式保存每个对象的名称。load()
恢复save()
编写的对象,并从?load
返回“创建的对象名称的字符 vector ”。在这种情况下,load()
恢复(在全局环境中创建)符号defaultPacks
,为其填充默认软件包的字符 vector ,并返回其具有的对象的名称(即长度为1的字符 vector “defaultPacks”)恢复。然后,返回值将覆盖恢复的值,并且我们有了defaultPacks = "defaultPacks"
。install.packages
的第一个参数毫无意义,它来自?install.packages
,是“应下载当前版本的软件包名称的字符 vector ”。字符 vector 恰好是符号defaultPacks
,但是错误来自符号的值,即字符 vector "defaultPacks"
。save()
和load()
或多或少必须以支持多个对象的方式工作。另一方面,saveRDS()
和readRDS()
(好的,为什么要读取而不是加载?)具有保存单个对象的协定。无需存储已保存对象的名称即可恢复与其关联的值。因此saveRDS(defaultPacks, fname); defaultPacks = readRDS(fname)
可以工作,尤其是在这一系列操作之前和之后defaultPacks
的值保持不变。> orig = defaultPacks = c("AER", "plyr", "dplyr")
> saveRDS(defaultPacks, fname)
> defaultPacks = readRDS(fname)
> identical(orig, defaultPacks)
[1] TRUE
毫无疑问,答案是“经验丰富的R程序员...您怎么做?”的答案。上面的
?
暗示了答案-仔细阅读本手册。而且,在基本R代码中,评估不符合标准的地方并不多-公式和library
是主要的罪魁祸首-因此认识到问题所在并不能帮助我们专注于实际发生的事情。