How can I read command line parameters from an R script?
我有一个R脚本,我想为它提供几个命令行参数(而不是代码本身的硬编码参数值)。该脚本在Windows上运行。
我找不到有关如何将命令行上提供的参数读取到R脚本中的信息。如果不能做到,我会很惊讶,所以也许我在谷歌搜索中没有使用最好的关键词…
有什么建议吗?
德克的答案就是你所需要的一切。这是一个最小的可重复的例子。
我做了两份文件:
exmpl.bat :1
2
3
4set R_Script="C:\Program Files
-3.0.2\bin
Script.exe"
%R_Script% exmpl.R 2010-01-28 example 100 > exmpl.batch 2>&1或者,使用
Rterm.exe :1
2
3
4set R_TERM="C:\Program Files
-3.0.2\bin\i386
term.exe"
%R_TERM% --no-restore --no-save --args 2010-01-28 example 100 < exmpl.R > exmpl.batch 2>&1exmpl.R :1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18options(echo=TRUE) # if you want see commands in output file
args <- commandArgs(trailingOnly = TRUE)
print(args)
# trailingOnly=TRUE means that only your arguments are returned, check:
# print(commandArgs(trailingOnly=FALSE))
start_date <- as.Date(args[1])
name <- args[2]
n <- as.integer(args[3])
rm(args)
# Some computations:
x <- rnorm(n)
png(paste(name,".png",sep=""))
plot(start_date+(1L:n), x)
dev.off()
summary(x)
将两个文件保存在同一目录中,并启动
example.png 有一些图- 完成了所有的工作
您还可以添加一个环境变量
1 2 3 | "C:\Program Files -3.0.2\bin Script.exe" |
在批处理脚本中使用它作为
RScript 的语法比较简单RScript 自动选择X64上的架构(详见R安装管理2.6子架构)- 如果要将命令写入输出文件,
RScript 需要.r文件中的options(echo=TRUE) 。
几点:
命令行参数为可通过
您可以在所有平台(包括Windows)上使用
cran上有两个附加包——getopt和optparse——都是为命令行解析而编写的。
2015年11月编辑:出现了新的备选方案,我衷心推荐Docopt。
将此添加到脚本顶部:
1 | args<-commandArgs(TRUE) |
然后,您可以将传递的参数称为
然后运行
1 | Rscript myscript.R arg1 arg2 arg3 |
如果参数是包含空格的字符串,请用双引号括起来。
尝试库(getopt)…如果你想要更好的话。例如:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | spec <- matrix(c( 'in' , 'i', 1,"character","file from fastq-stats -x (required)", 'gc' , 'g', 1,"character","input gc content file (optional)", 'out' , 'o', 1,"character","output filename (optional)", 'help' , 'h', 0,"logical", "this help" ),ncol=5,byrow=T) opt = getopt(spec); if (!is.null(opt$help) || is.null(opt$in)) { cat(paste(getopt(spec, usage=T)," ")); q(); } |
你需要一点(读作"小R")。
德克将在大约15分钟内赶到现场进行详细说明;)
由于在答案中多次提到
脚本:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | library(optparse) option_list <- list( make_option(c("-n","--count_lines"), action="store_true", default=FALSE, help="Count the line numbers [default]"), make_option(c("-f","--factor"), type="integer", default=3, help="Multiply output by this number [default %default]") ) parser <- OptionParser(usage="%prog [options] file", option_list=option_list) args <- parse_args(parser, positional_arguments = 1) opt <- args$options file <- args$args if(opt$count_lines) { print(paste(length(readLines(file)) * opt$factor)) } |
给定一个任意文件
在命令行上:
1 2 3 4 5 6 7 8 9 10 11 12 | Usage: script.R [options] file Options: -n, --count_lines Count the line numbers [default] -f FACTOR, --factor=FACTOR Multiply output by this number [default 3] -h, --help Show this help message and exit |
在bash中,您可以构建如下命令行:
1 2 3 4 5 6 7 8 | $ z=10 $ echo $z 10 $ Rscript -e"args<-commandArgs(TRUE);x=args[1]:args[2];x;mean(x);sd(x)" 1 $z [1] 1 2 3 4 5 6 7 8 9 10 [1] 5.5 [1] 3.027650 $ |
可以看到变量
仅供参考:有一个函数args(),它检索r函数的参数,不要与名为args的参数向量混淆。
我只是将一个好的数据结构和处理链组合在一起,以生成这种交换行为,不需要库。我确信它将被多次实现,并且在这个线程中找到了一些例子——我认为我会插手进来。
我甚至不需要特别的标志(这里唯一的标志是调试模式,创建一个变量,作为启动下游函数
1 2 | if ("--debug" %in% args) debug.mode <- T if ("-h" %in% args ||"--help" %in% args) |
其中,
它对于任何其他标志都是可重用的,您可以避免所有重复,并且没有库,因此没有依赖项:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 | args <- commandArgs(TRUE) flag.details <- list( "debug" = list( def ="Print variables rather than executing function XYZ...", flag ="--debug", output ="debug.mode <- T"), "help" = list( def ="Display flag definitions", flag = c("-h","--help"), output ="cat(help.prompt)") ) flag.conditions <- lapply(flag.details, function(x) { paste0(paste0('"',x$flag,'"'), sep =" %in% args", collapse =" ||") }) flag.truth.table <- unlist(lapply(flag.conditions, function(x) { if (eval(parse(text = x))) { return(T) } else return(F) })) help.prompts <- lapply(names(flag.truth.table), function(x){ # joins 2-space-separatated flags with a tab-space to the flag description paste0(c(paste0(flag.details[x][[1]][['flag']], collapse=" "), flag.details[x][[1]][['def']]), collapse="\t") } ) help.prompt <- paste(c(unlist(help.prompts),''),collapse=" ") # The following lines handle the flags, running the corresponding 'output' entry in flag.details for any supplied flag.output <- unlist(lapply(names(flag.truth.table), function(x){ if (flag.truth.table[x]) return(flag.details[x][[1]][['output']]) })) eval(parse(text = flag.output)) |
注意,在
样品输出:
1 2 3 4 | $ Rscript check_mail.Rscript --help --debug Print variables rather than executing function XYZ... -h --help Display flag definitions |
如果需要使用标记指定选项(如-h、-help、-number=42等),则可以使用r包optparse(源自python):http://cran.r-project.org/web/packages/optparse/vignettes/optparse.pdf.
至少我是这样理解你的问题的,因为我在寻找与bash getopt、perl getopt或python argparse和optparse等效的东西时找到了这篇文章。