我正在尝试编写一些具有嵌套结构的代码 - 例如一个脚本使用 source() 调用另一个脚本。
由于我有一个复杂的文件/文件夹结构,并且我希望代码可以在其他计算机上重现,所以我想使用动态路径(所以不是我计算机上的路径)。我想到了这个策略 - 有一个固定的文件夹结构,然后允许脚本在这个文件夹结构中“意识到它们在哪里”。
但是我遇到了一个问题,我不知道背后的原因。 这是一个可重现的示例。想想这个文件夹结构:
├── parent folder: file "test.R"
│ ├── ChildRMD (subfolder)
│ │ ├── "test2.R"
这是否令人困惑,基本上有一个包含文件“test.R”的父文件夹,然后该父文件夹中有一个名为“ChildRMD”的子文件夹。在“ChildRMD”中还有另一个 R 脚本“test2.R”。
这些是文件的内容。
# Get the path of the current R script
current_path <- dirname(rstudioapi::getActiveDocumentContext()$path)
setwd(current_path)
print(paste('Path in test is,',current_path))
#source(paste(current_path,'/ChildRMD/test2.R',sep=''))
# Get the path of the current R script
current_path <- dirname(rstudioapi::getActiveDocumentContext()$path)
setwd(current_path)
print(paste('Path in test2 is,',current_path))
如果我单独运行每个脚本,输出(请记住我评论了 test.R 中的“源”行,是:
"Path in test is, /Users/admin/Documents/temp"
"Path in test2 is, /Users/admin/Documents/temp/ChildRMD"
看起来一切都很好。基本上,这些文件使用 dirname() 函数来实现它们的位置。因此,如果我取消注释第一行(源代码),那么 test.R 看起来像:
# Get the path of the current R script
current_path <- dirname(rstudioapi::getActiveDocumentContext()$path)
setwd(current_path)
print(paste('Path in test is,',current_path))
source(paste(current_path,'/ChildRMD/test2.R',sep=''))
我只是运行 test.R (这将运行两个脚本,因为我在 test.R 中调用 test2.R),我得到:
[1] "Path in test is, /Users/admin/Documents/temp"
[1] "Path in test2 is, /Users/admin/Documents/temp"
这不是我所期望的,这将是:
[1] "Path in test is, /Users/admin/Documents/temp"
[1] "Path in test2 is, /Users/admin/Documents/temp/ChildRMD"
这基本上是我的问题的一个小例子。调用此 source() 命令似乎会影响文件表示其工作目录的方式,但无法说出原因。
有人建议使用这个包
here
,效果非常好!
如果我使用
library(here)
设置主目录,那么通过调用 here()
我会得到输出:
"/Users/admin/Documents/temp"
无论我处于层级中的哪个位置。 那么,
test.R
的路径将始终由here('test.R')
给出,而test2.R
的路径则由here('ChildRMD','test2.R')
给出。然后,我可以像这样修改 test.R
脚本:
# Get the path of the current R script
print(paste('Path in test is,',here('test.R')))
source(here('ChildRMD','test2.R'))
# Get the path of the current R script
print(paste('Path in test2 is,',here('ChildRMD','test2.R')))
如果我只运行 test.R 我有输出:
[1] "Path in test is, /Users/admin/Documents/temp/test.R"
[1] "Path in test2 is, /Users/admin/Documents/temp/ChildRMD/test2.R"
如果谁有更优雅的条件,欢迎在这里补充。