같은 디렉토리에있는 foo.R
다른 스크립트를 포함 하는 스크립트 가 있습니다 other.R
.
#!/usr/bin/env Rscript
message("Hello")
source("other.R")
그러나 현재 작업 디렉토리가 무엇이든 관계없이 R
찾고 싶습니다 other.R
.
즉, foo.R
자체 경로를 알아야합니다. 어떻게해야합니까?
답변
여기 에 문제에 대한 간단한 해결책이 있습니다. 이 명령은
script.dir <- dirname(sys.frame(1)$ofile)
현재 스크립트 파일의 경로를 반환합니다. 스크립트가 저장된 후에 작동합니다.
답변
이 commandArgs
함수를 사용하여 Rscript가 전달한 모든 옵션을 실제 R 인터프리터로 가져 와서 검색 할 수 --file=
있습니다. 스크립트가 경로에서 시작되었거나 전체 경로로 시작된 경우 script.name
아래는로 시작됩니다 '/'
. 그렇지 않으면cwd
전체 경로를 얻기 위해 두 경로를 연결할 수 있습니다.
편집 :script.name
위 의 내용 만 필요 하고 경로의 최종 구성 요소를 제거 하는 것처럼 들립니다 . 불필요한 cwd()
샘플을 제거하고 기본 스크립트를 정리 하고 내을 게시했습니다 other.R
. 이 스크립트와 other.R
스크립트를 동일한 디렉토리에 저장 chmod +x
하고 기본 스크립트를 실행하십시오.
main.R :
#!/usr/bin/env Rscript
initial.options <- commandArgs(trailingOnly = FALSE)
file.arg.name <- "--file="
script.name <- sub(file.arg.name, "", initial.options[grep(file.arg.name, initial.options)])
script.basename <- dirname(script.name)
other.name <- file.path(script.basename, "other.R")
print(paste("Sourcing",other.name,"from",script.name))
source(other.name)
other.R :
print("hello")
출력 :
burner@firefighter:~$ main.R
[1] "Sourcing /home/burner/bin/other.R from /home/burner/bin/main.R"
[1] "hello"
burner@firefighter:~$ bin/main.R
[1] "Sourcing bin/other.R from bin/main.R"
[1] "hello"
burner@firefighter:~$ cd bin
burner@firefighter:~/bin$ main.R
[1] "Sourcing ./other.R from ./main.R"
[1] "hello"
이것이 내가 dehmann이 찾고 있다고 믿는 것입니다.
답변
R 콘솔에서 ‘소스’할 때 Suppressingfire의 솔루션을 작동시킬 수 없었습니다.
Rscript를 사용할 때 hadley의 솔루션을 사용할 수 없었습니다.
두 세계의 최고?
thisFile <- function() {
cmdArgs <- commandArgs(trailingOnly = FALSE)
needle <- "--file="
match <- grep(needle, cmdArgs)
if (length(match) > 0) {
# Rscript
return(normalizePath(sub(needle, "", cmdArgs[match])))
} else {
# 'source'd via R console
return(normalizePath(sys.frames()[[1]]$ofile))
}
}
답변
frame_files <- lapply(sys.frames(), function(x) x$ofile)
frame_files <- Filter(Negate(is.null), frame_files)
PATH <- dirname(frame_files[[length(frame_files)]])
내가 잊어 버렸기 때문에 어떻게 작동하는지 묻지 마십시오.
답변
이것은 나를 위해 작동
library(rstudioapi)
rstudioapi::getActiveDocumentContext()$path
답변
라켄시 의 답R 스크립트의 경로 를 얻는 부터 가장 정확하고 정말 훌륭한 IMHO입니다. 그러나 여전히 더미 기능을 통합 한 핵입니다. 다른 사람들이 쉽게 찾을 수 있도록 여기에 인용하고 있습니다.
sourceDir <-getSrcDirectory (함수 (더미) {더미})
이것은 명령문이 배치 된 파일의 디렉토리를 제공합니다 (더미 함수가 정의 된 위치). 그런 다음 작업 direcory를 설정하고 상대 경로를 사용하는 데 사용할 수 있습니다.
setwd(sourceDir)
source("other.R")
또는 절대 경로를 만들려면
source(paste(sourceDir, "/other.R", sep=""))
답변
하나의 모든 것! (-RStudio 콘솔을 처리하도록 2019 년 1 월 1 일 업데이트 됨)
#' current script file (in full path)
#' @description current script file (in full path)
#' @examples
#' works with Rscript, source() or in RStudio Run selection, RStudio Console
#' @export
ez.csf <- function() {
# http://stackoverflow.com/a/32016824/2292993
cmdArgs = commandArgs(trailingOnly = FALSE)
needle = "--file="
match = grep(needle, cmdArgs)
if (length(match) > 0) {
# Rscript via command line
return(normalizePath(sub(needle, "", cmdArgs[match])))
} else {
ls_vars = ls(sys.frames()[[1]])
if ("fileName" %in% ls_vars) {
# Source'd via RStudio
return(normalizePath(sys.frames()[[1]]$fileName))
} else {
if (!is.null(sys.frames()[[1]]$ofile)) {
# Source'd via R console
return(normalizePath(sys.frames()[[1]]$ofile))
} else {
# RStudio Run Selection
# http://stackoverflow.com/a/35842176/2292993
pth = rstudioapi::getActiveDocumentContext()$path
if (pth!='') {
return(normalizePath(pth))
} else {
# RStudio Console
tryCatch({
pth = rstudioapi::getSourceEditorContext()$path
pth = normalizePath(pth)
}, error = function(e) {
# normalizePath('') issues warning/error
pth = ''
}
)
return(pth)
}
}
}
}
}