Tentukan jalur skrip pelaksana

255

Saya memiliki skrip bernama foo.Ryang menyertakan skrip lain other.R, yang ada di direktori yang sama:

#!/usr/bin/env Rscript
message("Hello")
source("other.R")

Tetapi saya ingin Rmenemukan bahwa other.Rapa pun direktori kerja saat ini.

Dengan kata lain, foo.Rperlu tahu jalannya sendiri. Bagaimana saya bisa melakukan itu?

jujur
sumber
2
Tidak. :( Saya belum melihat solusi apa pun yang benar-benar berfungsi. Terlepas dari solusi untuk hanya melewati direktori atau menggunakan variabel lingkungan.
Frank
3
Ini akan luar biasa untuk membuat skrip sepenuhnya portabel dan dapat dieksekusi oleh bahkan R neofites!
Etienne Low-Décarie
4
Tampaknya semua jawaban mengharuskan Anda untuk memasukkan jalur di beberapa titik (setidaknya untuk mencari file)! Alangkah baiknya jika Anda bisa mengirim folder terkompresi kepada seseorang dan menjalankan file skrip R apa pun di dalam folder itu yang akan dibaca dan disimpan ke folder itu.
Etienne Low-Décarie
10
masalah tunggal ini sebenarnya bisa menjadi alasan mengapa saya bisa sepenuhnya pindah ke Python
Giacomo
5
@giac_man, saya merasa R penuh dengan ratusan masalah kecil seperti ini yang semuanya membuat sulit untuk bekerja.
Michael Barton

Jawaban:

102

Di sini ada solusi sederhana untuk masalah tersebut. Perintah ini:

script.dir <- dirname(sys.frame(1)$ofile)

mengembalikan jalur file skrip saat ini. Ini berfungsi setelah skrip disimpan.

this.is.not.a.nick
sumber
4
Itu tidak bekerja untuk saya. Saya menjalankan R di Windows. Ada ide?
Ehsan88
4
Mendapat kesalahan yang sama, dengan skrip yang tersimpan dan baru diinstal dan menjalankan R 3.2.0 di windows ...
RalfB
27
Kesalahan ini terjadi ketika Anda mencoba mengeksekusi dirname(sys.frame(1)$ofile)langsung dari Rstudio. Ini berfungsi ok ketika skrip dieksekusi menggunakan sumber ("other.R"), dan dirname(sys.frame(1)$ofile)ada di dalam "other.R".
Murta
4
Saya mendapat kesalahan 'tidak banyak frame di stack' saat memanggil sebagai skrip dengan rscript.exe yaitu tidak menggunakan sumber (). jadi saya malah harus menggunakan solusi dari Suppressingfire di bawah ini
Mark Adamson
3
Saya gel NULLketika ini ditempatkan di server.R saat menggunakan mengkilap
Paul
75

Anda dapat menggunakan commandArgsfungsi ini untuk mendapatkan semua opsi yang diteruskan oleh Rscript ke penerjemah R aktual dan mencarinya --file=. Jika skrip Anda diluncurkan dari jalur atau jika diluncurkan dengan jalur lengkap, di script.namebawah ini akan dimulai dengan a '/'. Kalau tidak, itu harus relatif terhadapcwd dan Anda dapat menggabungkan kedua jalur untuk mendapatkan path lengkap.

Sunting: sepertinya Anda hanya membutuhkan yang di script.nameatas dan melepaskan komponen akhir dari path. Saya telah menghapus cwd()sampel yang tidak dibutuhkan dan membersihkan skrip utama dan memposting other.R. Simpan saja skrip dan other.Rskrip ini ke direktori yang sama chmod +x, dan jalankan skrip utama.

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)

lainnya.R :

print("hello")

keluaran :

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"

Inilah yang saya percaya yang dicari oleh dehmann.

Menekan api
sumber
Ada apa dengan downmod?
Suppressingfire
2
Saya downmodded karena teknik Anda tidak bekerja dengan sourceseperti yang saya pikir OP inginkan - tapi mungkin saya salah membaca persyaratannya. Tapi aku tidak bisa un-downmod :( Maaf!
hadley
Tetapi sebenarnya, itu bekerja dengan baik dengan sumber! Cukup sumber (nama lain) dan berfungsi dengan baik.
Suppressingfire
3
Untuk penggabungan jalur, lebih baik digunakanother.name <- file.path(script.basename, "other.R")
Jason
1
Ketika saya mencoba untuk menjalankan commandArgs(trailingOnly = FALSE)di dalam server. R dalam aplikasi yang mengkilap, saya dapatkan [1] "RStudio" "--interactive". Tidak ada informasi tentang direktori dari mana ia dipanggil.
Paul
57

Saya tidak bisa mendapatkan solusi Suppressingfire untuk bekerja ketika 'sumber' dari konsol R.
Saya tidak bisa mendapatkan solusi hadley untuk bekerja ketika menggunakan Rscript.

Terbaik dari kedua dunia?

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))
        }
}
kapal uap25
sumber
6
Saya suka ini karena ia bekerja dengan keduanya Rscriptdan source()dalam R. Saya sarankan melakukan normalizePath()pada kedua versi, sehingga memberikan jalan penuh dalam kedua kasus.
wch
1
Ini adalah satu-satunya hal yang berhasil. Catatan, agar hal ini berhasil, library(base)saya perlu waktu beberapa saat untuk mencari tahu lol
O.rka
2
Anda tuan mendapatkan suara saya, karena ini adalah solusi yang bekerja untuk saya
Vince W.
1
Jika ini membantu siapa pun, untuk posting asli, itu berarti source(file.path(dirname(thisFile()), "other.R"))di foo.R. Ini bekerja untuk saya.
Kim
Satu masalah. Misalkan dalam sumber RStudio I main.Ryang sumber helper.Rpanggilan thisFile(). Ini akan mengambil jalur main.Ralih-alih helper.R. Ada tips di sini?
Wassadamo
37
frame_files <- lapply(sys.frames(), function(x) x$ofile)
frame_files <- Filter(Negate(is.null), frame_files)
PATH <- dirname(frame_files[[length(frame_files)]])

Jangan tanya saya bagaimana cara kerjanya, karena saya sudah lupa: /

Hadley
sumber
2
Dalam konteks apa itu bekerja? print (sys.frames ()) muncul NULL ketika saya menjalankannya.
Suppressingfire
1
@Suppressingfire: sys.framesmengembalikan lingkungan tumpukan panggilan, jadi itu benar-benar masuk akal ketika dipanggil dari suatu fungsi. Coba, misalnya foo <- function() {bar <- function() print(sys.frames()); bar()}; foo(),. Saya tidak dapat menemukan kode @ hadley karena lingkungan tidak memiliki ofileanggota.
Richie Cotton
1
Anda harus sumber file di - yaitu jika saya menyimpan kode itu kemudian jalankan source("~/code/test.r"), PATHakan diatur ke ~/desktop. Jika Anda hanya mengevaluasinya di tingkat atas, itu akan mengembalikan NULL.
Hadley
4
Ini tidak menjawab pertanyaan saya. Saya perlu mencari file "other.R" secara otomatis. x$ofiletidak terdefinisi, jadi frame_fileskosong.
Frank
@Hadley, kode yang sangat berguna. Saya dapat menggeneralisasi fungsi utilitas "memuat ulang skrip" yang saya tambahkan ke hampir semua skrip ketika sedang dalam pengembangan aktif. Reloader RScript
Sim
29

Ini bekerja untuk saya

library(rstudioapi)    
rstudioapi::getActiveDocumentContext()$path
ColinTea
sumber
4
Ini hanya berfungsi dari dalam RStudio kurasa. Saya coba dari terminal Error: RStudio not running.
Ista
lebih khusus itu berfungsi, jika dijalankan dari script R di R studio. Bahkan pada konsol di RStudio tidak akan memberikan hasil yang tepat ""dalam kasus saya
Kay
Ini berfungsi saat berjalan secara interaktif di Rstudio selama Anda tidak mengubah dokumen dalam fokus . Jika Anda mengirimkan baris untuk dijalankan dan kemudian beralih ke dokumen lain saat dijalankan, jalur ke dokumen lain akan dikembalikan.
Patrick
26

Jawaban rakensi dari Getting path of R script adalah IMHO yang paling benar dan benar-benar brilian. Namun, ini masih merupakan hack yang menggabungkan fungsi dummy. Saya mengutipnya di sini, agar lebih mudah ditemukan oleh orang lain.

sourceDir <- getSrcDirectory (fungsi (dummy) {dummy})

Ini memberikan direktori file di mana pernyataan itu ditempatkan (di mana fungsi dummy didefinisikan). Kemudian dapat digunakan untuk mengatur direktori kerja dan menggunakan jalur relatif misalnya

setwd(sourceDir)
source("other.R")

atau untuk membuat jalur absolut

 source(paste(sourceDir, "/other.R", sep=""))
borgol
sumber
1
Bagi saya, solusi Anda adalah yang terbaik. Khususnya karena itu bisa diterapkan ke aplikasi Shiny dan yang di tautan tidak.
jcarlos
1
Di sini getSrcDirectory adalah utils :: getSrcDirectory
RubenLaguna
5
Ini mungkin bekerja dengan baik di Linux / Mac, tetapi itu tidak bekerja untuk saya dalam sesi RStudio interatif di Windows. sourceDirkosong.
Contango
1
@Contango di terminal interaktif, tidak ada jalan !!! Anda ingin path ke file.
pommedeterresautee
1
Saya mengerti character(0). Saran?
abalter
16

Semua dalam satu! (--01 / 09/2019 diperbarui untuk berurusan dengan RStudio Konsol)

#' 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)
                }
            }
        }
    }
}
Jerry T
sumber
Tidak berfungsi dengan sesi R interaktif; Saya mendapatkan: `` `> sumber (" csf.R ")> csf () Kesalahan: RStudio tidak menjalankan` ``
ManicMailman
Ini bagus. Bisakah seseorang membuat paket?
Joe Flack
Ini berfungsi saat berjalan secara interaktif di Rstudio selama Anda tidak mengubah dokumen dalam fokus. Jika Anda mengirimkan baris untuk dijalankan dan kemudian beralih ke dokumen lain saat dijalankan, jalur ke dokumen lain akan dikembalikan.
Patrick
13

Varian ramping dari jawaban Supressingfire:

source_local <- function(fname){
    argv <- commandArgs(trailingOnly = FALSE)
    base_dir <- dirname(substring(argv[grep("--file=", argv)], 8))
    source(paste(base_dir, fname, sep="/"))
}
momeara
sumber
Ini tidak bekerja secara rekursif; sumber file I mencari file data (tetapi dalam direktori yang salah).
The Unfun Cat
11

Ini bekerja untuk saya. Hanya mengeluarkannya dari argumen baris perintah, menghapus teks yang tidak diinginkan, melakukan dirname dan akhirnya mendapatkan path lengkap dari itu:

args <- commandArgs(trailingOnly = F)  
scriptPath <- normalizePath(dirname(sub("^--file=", "", args[grep("^--file=", args)])))
eddi
sumber
8

Saya telah membungkus dan memperluas jawaban untuk pertanyaan ini menjadi fungsi baru thisfile()di rprojroot . Juga berfungsi untuk merajut knitr.

krlmlr
sumber
6

Saya menyukai solusi steamer25 karena tampaknya yang paling kuat untuk tujuan saya. Namun, ketika debugging di RStudio (di windows), jalan tidak akan ditetapkan dengan benar. Alasannya adalah bahwa jika breakpoint diatur dalam RStudio, sumber file menggunakan perintah "sumber debug" alternatif yang menetapkan jalur skrip sedikit berbeda. Ini adalah versi final yang saat ini saya gunakan untuk akun mana perilaku alternatif ini dalam RStudio saat debugging:

# @return full path to this script
get_script_path <- function() {
    cmdArgs = commandArgs(trailingOnly = FALSE)
    needle = "--file="
    match = grep(needle, cmdArgs)
    if (length(match) > 0) {
        # Rscript
        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 {
            # Source'd via R console
            return(normalizePath(sys.frames()[[1]]$ofile))
        }
    }
}
aprstar
sumber
sumber di Rstudio memberi ofile untuk saya, tetapi debugSource memberi fileName sehingga solusi Anda bekerja dengan baik tetapi komentar kode tidak benar dalam kasus saya
Mark Adamson
6

Saya mencoba hampir semua hal dari pertanyaan ini, Mendapatkan jalur skrip R , Dapatkan jalur skrip saat ini , Temukan lokasi file .R saat ini dan perintah R untuk mengatur direktori kerja ke lokasi file sumber di Rstudio , tetapi pada akhirnya menemukan diri saya secara manual menelusuri tabel CRAN dan menemukan

scriptName Perpustakaan

yang menyediakan current_filename()fungsi, yang mengembalikan jalur skrip lengkap yang tepat saat sumber di RStudio dan juga ketika menjalankan melalui R atau RScript yang dapat dieksekusi.

Bojan P.
sumber
2
Package ‘scriptName’ was removed from the CRAN repository.- apa sekarang? : o
Bojan P.
3

Saya juga memiliki masalah ini, dan tidak ada solusi di atas yang berfungsi untuk saya. Mungkin dengan sourceatau hal-hal seperti itu, tetapi itu tidak cukup jelas.

Saya menemukan ini, bagi saya anggun, solusi:

paste0(gsub("\\", "/", fileSnapshot()$path, fixed=TRUE),"/")

Yang penting dalam hal itu adalah fileSnapshot()memberi Anda banyak informasi tentang file. Ia mengembalikan daftar 8 elemen. Ketika Anda memilih pathsebagai elemen daftar, jalan dikembalikan dengan \\sebagai pemisah, sehingga sisa kode hanya untuk mengubahnya.

Saya harap ini membantu.

Antoine
sumber
1
Ini tidak bekerja untuk saya di mesin Linux; alih-alih mengembalikan jalur file, itu mengembalikan direktori tempat saya berada saat ini. Saya membuat skrip uji yang disebut TEST.R dengan satu baris kode: print (fileSnapshot () $ path) Saya menyimpannya di folder ini: / opt / home / boops / Desktop / Testfolder / TEST.RI kemudian menavigasi ke desktop saya dan mencoba menjalankan file: boops @ linuxserver: ~ / Desktop $ Rscript /opt/home/boops/Desktop/Testfolder/TEST.R [1 ] "/ opt / home / boops / Desktop"
Boops Boops
Juga tidak bekerja untuk saya. Mengembalikan hal yang sama dengan 'di sini ()' saat menggunakan perpustakaan 'di sini'. Ia mengembalikan jalur ke proyek R saya yang saat ini terbuka, tetapi bukankah dia sendiri yang mengajukannya.
Joe Flack
2

Anda dapat membungkus skrip r dalam skrip bash dan mengambil jalur skrip sebagai variabel bash seperti:

#!/bin/bash
     # [environment variables can be set here]
     path_to_script=$(dirname $0)

     R --slave<<EOF
        source("$path_to_script/other.R")

     EOF
ennuikiller
sumber
3
Ini mengharuskan Anda memiliki jalur skrip. Itu tidak memungkinkan Anda untuk membuat skrip R yang benar-benar portabel yang dapat dijalankan dari mana saja.
Etienne Low-Décarie
@ EtienneLow-Décarie Ini tidak memerlukan jalur skrip, ia mendapatkannya dari bash. Masalah utama adalah bahwa itu bukan cara yang dapat diandalkan untuk mendapatkan jalan. Sesuatu seperti ini lebih disukai, seperti pada stackoverflow.com/questions/59895/… path_to_script = "$ (cd" $ (dirname "$ {BASH_SOURCE [0]}") "&& pwd)"
John Haberstroh
2

Saya suka pendekatan ini:

this.file <- sys.frame(tail(grep('source',sys.calls()),n=1))$ofile
this.dir <- dirname(this.file)
kuna.matata
sumber
2

Saya baru saja menyelesaikan ini sendiri. Untuk memastikan portabilitas skrip Anda selalu mulai dengan:

wd <- setwd(".")
setwd(wd)

Ini bekerja karena "." diterjemahkan seperti perintah Unix $ PWD. Menetapkan string ini ke objek karakter memungkinkan Anda untuk kemudian memasukkan objek karakter tersebut ke setwd () dan Presto kode Anda akan selalu berjalan dengan direktori saat ini sebagai direktori kerja, tidak peduli di mana mesin itu berada atau di mana dalam struktur file itu. terletak. (Bonus tambahan: Objek wd dapat digunakan dengan file.path () (mis. File.path (wd, "output_directory") untuk memungkinkan pembuatan direktori output standar terlepas dari jalur file yang mengarah ke direktori yang Anda beri nama. Ini memang mengharuskan Anda untuk membuat direktori baru sebelum merujuknya dengan cara ini tetapi itu juga dapat dibantu dengan objek wd.

Bergantian, kode berikut melakukan hal yang sama persis:

wd <- getwd()
setwd(wd)

atau, jika Anda tidak memerlukan path file dalam suatu objek, Anda cukup:

setwd(".")
Andrew Moffat Jr.
sumber
11
Nggak. Itu menemukan direktori proses, bukan file itu sendiri.
user1071847
Ini bekerja untuk saya di Windows dengan RStudio dalam mode interaktif.
Contango
2

Perhatikan bahwa paket getopt menyediakan get_Rscript_filenamefungsi, yang hanya menggunakan solusi yang sama dengan yang disajikan di sini, tetapi sudah ditulis untuk Anda dalam modul R standar, jadi Anda tidak perlu menyalin dan menempelkan fungsi "get path path" ke setiap skrip Anda menulis.

Ryan C. Thompson
sumber
Itu selalu mengembalikan NA, bahkan jika saya membuat skrip yang mencetak hasilnya dan kemudian memanggil skrip misalnya denganR -e "library(getopt); testscript.R"
bokov
1
Sesuai dengan namanya, Anda harus menjalankan skrip menggunakan Rscript.
Ryan C. Thompson
Ah, oops. Terima kasih.
bokov
1

Lihat findSourceTraceback()dari R.utils paket, yang

Menemukan semua objek 'srcfile' yang dihasilkan oleh sumber () di semua bingkai panggilan. Ini memungkinkan untuk mengetahui file mana yang saat ini ditulis oleh sumber ().

HenrikB
sumber
1

Saya memiliki masalah dengan implementasi di atas karena skrip saya dioperasikan dari direktori yang disinkronkan, atau setidaknya itu sebabnya saya pikir solusi di atas tidak bekerja untuk saya. Sejalan dengan jawaban @ ennuikiller, saya membungkus Rscript saya dengan bash. Saya mengatur variabel path menggunakan pwd -P, yang menyelesaikan struktur direktori yang disinkronkan. Kemudian masukkan path ke dalam Rscript.

Bash.sh

#!/bin/bash

# set path variable
path=`pwd -P`

#Run Rscript with path argument
Rscript foo.R $path

untukR

args <- commandArgs(trailingOnly=TRUE)
setwd(args[1])
source(other.R)
Luke Singham
sumber
1

Saya akan menggunakan varian dari pendekatan @ steamer25. Intinya adalah bahwa saya lebih suka mendapatkan skrip bersumber terakhir bahkan ketika sesi saya dimulai melalui Rscript. Cuplikan berikut, ketika disertakan pada file, akan memberikan variabel yang thisScriptberisi jalur normalisasi skrip. Saya mengakui (ab) penggunaan sumber, jadi kadang-kadang saya meminta Rscript dan skrip yang disediakan dalam --fileargumen sumber skrip lain yang sumber lain ... Suatu hari saya akan berinvestasi dalam membuat kode berantakan saya berubah menjadi sebuah paket.

thisScript <- (function() {
  lastScriptSourced <- tail(unlist(lapply(sys.frames(), function(env) env$ofile)), 1)

  if (is.null(lastScriptSourced)) {
    # No script sourced, checking invocation through Rscript
    cmdArgs <- commandArgs(trailingOnly = FALSE)
    needle <- "--file="
    match <- grep(needle, cmdArgs)
    if (length(match) > 0) {
      return(normalizePath(sub(needle, "", cmdArgs[match]), winslash=.Platform$file.sep, mustWork=TRUE))
    }
  } else {
    # 'source'd via R console
    return(normalizePath(lastScriptSourced, winslash=.Platform$file.sep, mustWork=TRUE))
  }
})()
Ailton Andrade de Oliveira
sumber
1

99% dari kasus yang mungkin Anda gunakan:

sys.calls()[[1]] [[2]]

Ini tidak akan berfungsi untuk panggilan gila di mana skrip bukan argumen pertama, yaitu source(some args, file="myscript"),. Gunakan @ hadley dalam kasus mewah ini.

antonio
sumber
Bukan dari dalam RStudio, kecuali, saat sumber
nJGL
1

Pendekatan Steamer25 bekerja, tetapi hanya jika tidak ada spasi putih di jalur. Pada macOS setidaknya cmdArgs[match]mengembalikan sesuatu seperti /base/some~+~dir~+~with~+~whitespace/untuk/base/some\ dir\ with\ whitespace/ .

Saya mengatasi ini dengan mengganti "~ + ~" dengan spasi putih sebelum mengembalikannya.

thisFile <- function() {
  cmdArgs <- commandArgs(trailingOnly = FALSE)
  needle <- "--file="
  match <- grep(needle, cmdArgs)
  if (length(match) > 0) {
    # Rscript
    path <- cmdArgs[match]
    path <- gsub("\\~\\+\\~", " ", path)
    return(normalizePath(sub(needle, "", path)))
  } else {
    # 'source'd via R console
    return(normalizePath(sys.frames()[[1]]$ofile))
  }
}

Jelas Anda masih dapat memperpanjang blok lain seperti yang dilakukan aprstar.

iball
sumber
1

Jika daripada skrip, foo.Rmengetahui lokasi jalurnya, jika Anda dapat mengubah kode untuk selalu merujuk semua sourcejalur dari yang umum, rootmaka ini mungkin sangat membantu:

Diberikan

  • /app/deeply/nested/foo.R
  • /app/other.R

Ini akan bekerja

#!/usr/bin/env Rscript
library(here)
source(here("other.R"))

Lihat https://rprojroot.r-lib.org/ untuk cara mendefinisikan akar proyek.

mmell
sumber
Bagi saya paket di sini melakukan pekerjaan dengan tepat dan tampaknya menjadi solusi yang mudah
Ron
0
#!/usr/bin/env Rscript
print("Hello")

# sad workaround but works :(
programDir <- dirname(sys.frame(1)$ofile)
source(paste(programDir,"other.R",sep='/'))
source(paste(programDir,"other-than-other.R",sep='/'))
kinjelom
sumber
Saya masih mendapatkan kesalahan "Kesalahan dalam sys.frame (1): tidak banyak frame di stack"
Michael Barton
0

Luar biasa tidak ada struktur tipe '$ 0' di R! Anda dapat melakukannya dengan system () panggilan ke skrip bash yang ditulis dalam R:

write.table(c("readlink -e $0"), file="scriptpath.sh",col=F, row=F, quote=F)
thisscript <- system("sh scriptpath.sh", intern = TRUE)

Kemudian cukup bagikan nama scriptpath.sh untuk other.R

splitstr <- rev(strsplit(thisscript, "\\/")[[1]])
otherscript <- paste0(paste(rev(splitstr[2:length(splitstr)]),collapse="/"),"/other.R")
bruce.moran
sumber
Saya mendapatkan pesan kesalahanreadLink: illegal option -- e usage: readLink [-FlLnqrsx] [-f format] [-t timefmt] [file ...]
altabq
0

Dengan melihat tumpukan panggilan kita bisa mendapatkan filepath dari setiap skrip yang dieksekusi, dua yang paling berguna mungkin akan menjadi skrip yang sedang dieksekusi, atau skrip pertama yang bersumber (entri).

script.dir.executing = (function() return( if(length(sys.parents())==1) getwd() else dirname( Filter(is.character,lapply(rev(sys.frames()),function(x) x$ofile))[[1]] ) ))()

script.dir.entry = (function() return( if(length(sys.parents())==1) getwd() else dirname(sys.frame(1)$ofile) ))()
pengguna425678
sumber