【问题标题】:How to set a function that makes operations between columns (within a dataframe)如何设置在列之间进行操作的函数(在数据框中)
【发布时间】:2019-07-18 22:04:33
【问题描述】:

问题

我正在制作一个函数来描述给定时间序列的时间状态变化。 它会说给定列的值是否大于、小于、等于前一个,并打印结果: 它可以在同一个数据框或其他不同的对象中。我正在做 它可以转换数据以便有利于生存分析。

做了什么

我已经制作了一个 if else 阶梯,如下所示:其中 (x) 是数据帧中的第 i 列,(y) 是它之前的列 (i-1)。但是,我不知道如何定义函数的第一行以在数据框的每一列中实际执行此操作(从第二列开始计算),也不要与最后一列崩溃

func_name <- function (x, columns) {
if (x == NA) {
print("gone")
} else if (x < y) {
print("less")
} else if (x > y) {
print("more")
} else if (x = y) {
print("same")
} else {
print ("")
}
}

预期结果

理想情况下会像这样进行改造:

Id <- c(1,2,3)
Time1 <- c(3,3,4)
Time2 <- c(2,5,4)
Time3 <- c(1,5,8)
df <- data.frame(Id,Time1,Time2,Time3)
df

变成这样:

Id <- c(1,2,3)
Time1 <- c(3,3,4)
Time2 <- c("Less","More","Same")
Time3 <- c("Less","Same","More")
df2 <- data.frame(Id,Time1,Time2,Time3)
df2

任何帮助,非常感谢!

解决方案:@Andrew 和 @Cole 解决方案都可以解决问题!

【问题讨论】:

    标签: r dataframe dplyr tidyverse


    【解决方案1】:

    这听起来像是您正在寻找的东西。它不是自定义功能,但如果您需要,可以对其进行调整。希望这可以帮助!

    # Select the columns you need. NOTE: used [-1] to remove starting time column
    cols <- grep("Time", names(df), fixed = T)[-1]
    
    # Use case_when with your conditions
    df[cols] <- lapply(cols, function(i) dplyr::case_when(
      is.na(df[i]) ~ "Gone",
      df[i] > df[i-1] ~ "More",
      df[i] < df[i-1] ~ "Less",
      df[i] == df[i-1] ~ "Same"
    ))
    
    df
      Id Time1 Time2 Time3
    1  1     3  Less  Less
    2  2     3  More  Same
    3  3     4  Same  More
    

    【讨论】:

    • 我认为你需要df[cols[2:3]] &lt;- lapply(cols[2:3],它将产生 OP 的预期输出。
    • @Matt 很好的想法,但是代码应该已经通过在创建列向量时使用 [-1] 来处理这个问题。但我更新了我的评论,使其更有用/更清晰
    • 每列都有Time2More,这让我大吃一惊。
    • 啊,好眼光@Matt,看起来我在粘贴之前重新运行了更改后的数据帧(在我已经运行过一次代码之后)。很好!
    • 干杯!它确实有效,而且很容易扩展!非常感谢您的帮助!
    【解决方案2】:

    下面是 mapply 的用法和内部的匿名函数:

    df <- data.frame(Id,Time1,Time2,Time3)
    
    df[, 3:4] <- mapply(function(x, y) ifelse(y < x , 'Less', ifelse(y > x, 'More', 'Same'))
                        , df[, 2:3]
                        , df[, 3:4])
    df
    

    mapply 将遍历数据集的每个字段并应用一个函数。换句话说,我要区分df[, 2]df[, 3],然后是df[, 3]df[, 4]。我也可以这样做:

    fx_select <- function(x, y) {
    ifelse(y < x, 'Less', ifelse(y > x, 'More', 'Same'))
    }
    
    df[, 3:4] <- mapply(fx_select, df[, 2:3], df[, 3:4])
    

    还有一种方法:

    df[3:4] <- lapply(sign(df[2:3] - df[3:4]) + 2,
           function(x) c('More', 'Same', 'Less')[x]
           )
    

    【讨论】:

    • 干杯伙伴!干杯!它确实有效,同样!高度赞赏帮助。第一秒产生了一些有趣的结果!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-02-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-10-30
    • 2022-01-09
    相关资源
    最近更新 更多