【问题标题】:R: Transforming a vector into a list of argumentsR:将向量转换为参数列表
【发布时间】:2019-02-11 03:47:47
【问题描述】:

我想将函数应用于向量。但是,该函数需要一系列参数。因此,我需要将向量“拆分”为不相关的参数。

假设我有一个名为 dta 的数据框。我想运行一个函数,比如 mean 在它的一个列上,比如 DV。

下面显示问题

call("mean", dta$DV)

返回

mean(c(0.371, -0.860, etc... ))

该列是一个向量这一事实与 mean 函数不兼容,该函数需要一系列参数,而不是组合。

如果将“mean”替换为包含字符串的变量,则该解决方案应该有效,例如

fun <- "mean"

call( fun, dta$DV)

【问题讨论】:

  • 好吧,我假设你的意思是“一个函数”,而不是mean,因为它实际上需要一个向量,而不是一系列参数。对于mean,我会使用do.call("mean", list(dta$DV))。但是如果你有一个相反的函数(需要单例参数),你可以使用do.call("otherfunc", as.list(dta$DV))。是这个意思吗?
  • 好的,所以我可能没有理解这个问题。不过,为什么上面的调用没有返回一个数字?
  • 如果您阅读 ?call,它会说 "'call' 返回未评估的函数调用",其中“未评估”是关键。你可以做eval(call(...))(返回平均值),但你也可以像我之前的评论一样做do.call(...)
  • @r2evans:如果您将评论放入答案中,我将对其进行验证。感谢您的反馈。

标签: r


【解决方案1】:

R 具有不完全一致的功能。例如,minmax 接受任意数量的参数,其中所有无法识别的参数都在数学计算中考虑。 mean 不是,它必须将所有数字视为第一个(或命名为 x=)参数。

min(1,20,0)
# [1] 0
min(c(1,20,0))
# [1] 0
mean(1,20,0) # might not be what one would expect
# [1] 1
mean(c(1,20,0))
# [1] 7

为了好奇,20 和 0 不会被忽略,第一个 mean 调用被解释为 mean(0, trim=20, na.rm=0)(其中 na.rm=0 实际上与 na.rm=FALSE 相同)。

您对call 的使用有点不对劲。来自?call的帮助,

调用返回一个未计算的函数调用

这对你没有多大帮助。您可能会使用eval(call(...)),但鉴于下一个功能,这似乎很愚蠢。

do.call 的使用更直接一些。我可以将其作为第一个参数:一个函数(匿名或命名)或与函数匹配的字符串。使用其中一种之间实际上存在速度差异,因此我倾向于在可能的情况下使用character 对函数名称的引用。 (我不记得量化这个断言的参考,如果我很快找到它,我会包括它。)

对于像上面的min 这样可以接受任意数量的参数的函数,可以这样做:

args <- c(1,20,0)

as.list(args)
# [[1]]
# [1] 1
# [[2]]
# [1] 20
# [[3]]
# [1] 0
do.call("min", as.list(args)) # == min(1,20,0)
# [1] 0

list(args)
# [[1]]
# [1]  1 20  0
do.call("min", list(args)) # == min(c(1,20,0))
# [1] 0

但是,对于mean 和类似的,您需要强制执行后一种行为:

do.call("mean", list(args)) # == mean(c(1,20,0))
# [1] 7

要使用程序定义的参数调用函数,您需要使用do.call

【讨论】:

    猜你喜欢
    • 2012-07-17
    • 1970-01-01
    • 1970-01-01
    • 2021-12-25
    • 1970-01-01
    • 2021-01-18
    • 1970-01-01
    • 1970-01-01
    • 2017-08-22
    相关资源
    最近更新 更多