【问题标题】:How to read user input into the subset command如何将用户输入读入子集命令
【发布时间】:2014-05-21 23:02:51
【问题描述】:

我有一些这样的 R 命令

subset(
  (aggregate(cbind(var1,var2)~Ei+Mi+hours,a, FUN=mean)),
  (aggregate(cbind(var1,var2)~Ei+Mi+hours,a, FUN=mean))$Ei == c(1:EXP)
)

我想做

1) 要求用户输入var1var2

2) 将这些变量放入子集命令行,如上所示,然后 继续做其他事情。

注意:为了读取用户输入,我有类似的变量 c(ax,bx,cx,dx,ex,fx,gx,hx,ix,jx,kx,lx,mx,nx,ox) = c(1:15) 和每个 变量映射到数字 1 到 15。因此为用户和 要求用户选择 1 到 15 之间的任何数字,然后 检查输入数字的相应变量和 我认为将其读入命令行是最好的方法。

那么我该如何实现呢?

关于答案: 只是想知道有一种可能的情况,例如,如果用户想一次性输入多个数字。 [例如:1,2,3]...而不是如何使用 readlines 阅读此内容,如下面的答案中所述,使用

v1 <- quote(var1 <- as.numeric(readline('Enter Variable 1: ')))
eavl(v1)
xx <- paste0(letters[1:15], 'x')
xx[v1]

这种情况下如何读取多个变量?

【问题讨论】:

  • 为什么不要求用户填写您设置所有参数的配置文件(csv 或其他)?
  • 哦,这是一个简单的方法,而不是询问用户选项然后处理它。实际上我有 5 个不同的选项告诉用户选择任何一个,这样我就可以跳转到特定的功能并执行操作(所有这 5 种类型只是不同类型的图,需要不同类型的用户输入),所以基本上我将 csv 的值存储在数据框中并相应地读取它们并执行操作,这就是您的意思吗?
  • 是的,例如。您还应该使用带有默认值参数的函数。

标签: r dataframe


【解决方案1】:

这是readline 交互式提示的粗略示例。在评估v1 时,将提示用户输入一个值。然后将该值存储为var1

> v1 <- quote(var1 <- as.numeric(readline('Enter Variable 1: ')))
> eval(v1)
Enter Variable 1: 1000     ## user enters 1000, for example
> 100 + var1 + 50          ## example to show captured output as object
## [1] 1150

所以在你的情况下它可能会像

> v1 <- quote(var1 <- as.numeric(readline('Enter a number from 1 to 15: ')))
> eval(v1)
Enter a number from 1 to 15: 7
> var1
## [1] 7
> xx <- paste0(letters[1:15], 'x')
> xx
## [1] "ax" "bx" "cx" "dx" "ex" "fx" "gx" "hx" "ix" "jx" "kx" "lx" "mx" "nx" "ox"
> xx[var1]
## [1] "gx"

我从this older SO post 借用了这个想法来创建一个函数。您可以不可见地返回输出,它仍然会接收用户值。

input.fun <- function(){
     v1 <- readline("var1: ")  
     v2 <- readline("var2: ")
     v3 <- readline("var3: ")
     v4 <- readline("var4: ")
     v5 <- readline("var5: ")
     out <- sapply(c(v1, v2, v3, v4, v5), as.numeric, USE.NAMES = FALSE)
     invisible(out)    
}

> x <- input.fun()
var1: 7
var2: 4
var3: 8
var4: 5
var5: 2
> x
[1] 7 4 8 5 2

回应您的编辑:我不确定这是否是在一行中读取多个数字的标准方法,但它有效。

> xx <- readline('Enter numbers separated by a space: ')
Enter numbers separated by a space: 4 12 67 9 2
> as.numeric(strsplit(xx, ' ')[[1]])
## [1]  4 12 67  9  2

【讨论】:

  • 谢谢这很简单...我没想到..:)...我想向用户询问 5 个选项,然后根据用户选择的选项转移流量。那么我可以知道R中是否有一种开关功能可以做到这一点?或您建议的任何简单方法?再次感谢您的帮助。
  • 是的..:) 在 SO stackoverflow.com/questions/10393508/… 谢谢。
  • 哈哈,我只是在看那个。我添加了一些你可能会觉得有用的东西。
  • @statisticalbeginner 我对您的编辑发表了回复
  • @RichardScriven 这绝对是我想要的谢谢..:)
【解决方案2】:

这是使用scan()的可能性

#sample data
df<-data.frame(
    ax=runif(50),
    bx=runif(50),
    cx=runif(50),
    dx=runif(50),
    Ei=sample(letters[1:5], 50, replace=T)
)

#get vars
vars<-c(NA,NA)
while(any(is.na(vars))) {
    cat(paste("enter var number", sum(!is.na(vars))+1),"\n")
    cat(paste(seq_along(names(df)), ":", names(df)), sep="\n")
    try(n<-scan(what=integer(), nmax=1), silent=T)
    vars[min(which(is.na(vars)))]<-n
}
#--pause

#use vars
subset(aggregate(df[,vars], df[,c("Ei"), drop=F], FUN=mean), Ei=="a")

它不是超级健壮,但是如果您复制前半部分(在暂停之前),它会要求您输入两个变量数字,然后如果您运行后半部分,它将使用这两个值。我已经调整了 aggregatesubset 以更适合变量使用,这意味着不使用公式语法。

我没有做任何错误检查。这留给提问者做练习。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-05-26
    • 2010-09-09
    • 1970-01-01
    • 1970-01-01
    • 2021-10-13
    • 1970-01-01
    • 2021-09-18
    相关资源
    最近更新 更多