【问题标题】:Accessing multiple outputs in a function, combined with dplyr在一个函数中访问多个输出,结合 dplyr
【发布时间】:2017-05-15 08:54:59
【问题描述】:

我有这样的功能:

computeLagError <- function(x, y)
{
    until = length(x)

    msd.t <- rep(0,until)
    sd.t  <- rep(0,until)

    for (dt in 1:until)
    {
        displacement.x <- as.vector(na.omit(x[(1+dt):length(x)]) - x[1:(length(x)-dt)])
        displacement.y <- as.vector(na.omit(y[(1+dt):length(y)]) - y[1:(length(y)-dt)])
        sqrdispl <- (displacement.x^2 + displacement.y^2)
        msd.t[dt] <- mean(sqrdispl)
        sd.t[dt] <- sd(msd.t) # The error increases for every point, as time lag has fewer points
    }
    data_table <- as.data.table(msd.t, sd.t, sqrdispl)

    return(data_table)
}

我想返回三个值 msd.t、sd.t 和 sqrdispl 用于 dplyr。

df <- df %>% group_by(track_id) %>% mutate(msd = computeLagError(x, y)[,1],
                                           lag = seq_along(msd),
                                           stepsize = computeLagError(x, y)[,2],
                                           lag_error = computeLagError(x,y)[,3])

但我收到错误说子集不适用于函数。如果我尝试将值作为列表返回,我只能以某种方式访问​​每个列表中的第一个元素。

到目前为止,我的解决方案是让 3 个单独的函数返回 3 个不同的值,但这似乎很 hacky。上面甚至调用了我的函数 3 次,而我想调用它一次并访问值。

【问题讨论】:

  • 函数运行 3 次看起来有些低效。您是否考虑过使用dplyr::do(或purrr)代替mutate?

标签: r dplyr


【解决方案1】:

您的函数中有一些错误。例如,您返回包 data.table 而不是定义的数据表。载体的结合也不起作用。检查这个:

computeLagError <- function(x, y)
{
    until = length(x)

    msd.t <- rep(0,until)
    sd.t  <- rep(0,until)

    for (dt in 1:until)
    {
        displacement.x <- as.vector(na.omit(x[(1+dt):length(x)]) - x[1:(length(x)-dt)])
        displacement.y <- as.vector(na.omit(y[(1+dt):length(y)]) - y[1:(length(y)-dt)])
        sqrdispl <- (displacement.x^2 + displacement.y^2)
        msd.t[dt] <- mean(sqrdispl)
        sd.t[dt] <- sd(msd.t) # The error increases for every point, as time lag has fewer points
    }
    data_table <- cbind.data.frame(msd.t, sd.t, sqrdispl)

    return(data_table)
}

一些示例数据:

df = data.frame(track_id=as.factor(rep(c(1,2),each=50)),x=c(1:100),y=c(1:100))

您的代码:

df <- df %>% group_by(track_id) %>% mutate(msd = computeLagError(x, y)[,1],
                                           lag = seq_along(msd),
                                           stepsize = computeLagError(x, y)[,2],
                                           lag_error = computeLagError(x,y)[,3])

【讨论】:

  • 哎呀。我不知道月经是怎么来的。这里才星期一早上。更新主帖,因为这是一个令人眼花缭乱的错误。
  • 无论如何,谢谢。有用。但这会调用同一个函数 3 次,每次访问不同的列,对吧?
  • Same here :) 是的。嗯,最简单的方法是分配给一个对象并相应地选择列,但我不确定这在 dplyr 中是否可行。我去看看
猜你喜欢
  • 2019-12-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-07-26
相关资源
最近更新 更多