【问题标题】:How to create an equation in the dplyr::mutate function in R?如何在 R 的 dplyr::mutate 函数中创建方程?
【发布时间】:2018-05-18 02:14:55
【问题描述】:

我有一个关于在我的真实项目中使用 mutate 函数的问题。我的数据如下。

group time A_1 A_3 B_1 B_3 C_1 C_3
1     100  7   5   7   3   5   3
1     200  8   4   5   6   1   2
1     300  5   6   8   9   2   1
1     400  3   5   7   8   2   1
2     100  3   5   7   6   3   2
2     200  4   5   6   0   1   4
2     300  3   3   4   5   3   2
2     400  6   5   3   1   3   7

我将数据集称为 dat。我正在尝试计算每个 A、B 或 C 类型的两列之间的差异,即 A_diff = A_1 - A_3、B_diff = B_1 - B_3、C_diff = C_1 - C_3 等。我有比这里显示的更多类型和有多少不同的类型是不固定的。所以我想用下面的代码在mutate函数中做一个灵活的方程。

type = c("A", "B", "C")
for(i in type){
    dat = mutate(dat, paste(i, "_diff", sep = "") = paste(i, "_1", sep = "") -  paste(i, "_3", sep = "")  
}

但是,我收到一条错误消息,显示意外的“=”。

Error: unexpected '=' in "dat = mutate(dat, paste(i, "diff", sep = "") ="

请帮我改正。我也试过 cat 而不是 paste。

【问题讨论】:

    标签: r dplyr


    【解决方案1】:

    一种基于gatherspread计算差异然后left_join到原始数据框的解决方案。

    library(dplyr)
    library(tidyr)
    
    dat2 <- dat %>%
      gather(Column, Value, -group, -time) %>%
      separate(Column, into = c("Letter", "Number"), sep = "_") %>%
      spread(Number, Value) %>%
      mutate(Diff = `1` - `3`) %>%
      mutate(Letter = paste0(Letter, "_diff")) %>%
      select(-`1`, -`3`) %>%
      spread(Letter, Diff) %>%
      left_join(dat, ., by = c("group", "time"))
    dat2
    #   group time A_1 A_3 B_1 B_3 C_1 C_3 A_diff B_diff C_diff
    # 1     1  100   7   5   7   3   5   3      2      4      2
    # 2     1  200   8   4   5   6   1   2      4     -1     -1
    # 3     1  300   5   6   8   9   2   1     -1     -1      1
    # 4     1  400   3   5   7   8   2   1     -2     -1      1
    # 5     2  100   3   5   7   6   3   2     -2      1      1
    # 6     2  200   4   5   6   0   1   4     -1      6     -3
    # 7     2  300   3   3   4   5   3   2      0     -1      1
    # 8     2  400   6   5   3   1   3   7      1      2     -4
    

    或者您可以使用以下基于lapply的方法。

    re <- lapply(c("A", "B", "C"), function(x){
      dat[[paste0(x, "_1")]] - dat[[paste0(x, "_3")]]
    })
    
    names(re) <- paste0(c("A", "B", "C"), "_diff")
    
    dat2 <- cbind(dat, as.data.frame(re))
    dat2
    #   group time A_1 A_3 B_1 B_3 C_1 C_3 A_diff B_diff C_diff
    # 1     1  100   7   5   7   3   5   3      2      4      2
    # 2     1  200   8   4   5   6   1   2      4     -1     -1
    # 3     1  300   5   6   8   9   2   1     -1     -1      1
    # 4     1  400   3   5   7   8   2   1     -2     -1      1
    # 5     2  100   3   5   7   6   3   2     -2      1      1
    # 6     2  200   4   5   6   0   1   4     -1      6     -3
    # 7     2  300   3   3   4   5   3   2      0     -1      1
    # 8     2  400   6   5   3   1   3   7      1      2     -4
    

    数据

    dat <- read.table(text = "group time A_1 A_3 B_1 B_3 C_1 C_3
    1     100  7   5   7   3   5   3
    1     200  8   4   5   6   1   2
    1     300  5   6   8   9   2   1
    1     400  3   5   7   8   2   1
    2     100  3   5   7   6   3   2
    2     200  4   5   6   0   1   4
    2     300  3   3   4   5   3   2
    2     400  6   5   3   1   3   7",
                      header = TRUE, stringsAsFactors = FALSE)
    

    【讨论】:

      【解决方案2】:

      使用@www的数据你也可以试试

      res <- sapply(seq(3, ncol(dat), 2), function(x, y)  y[x] - y[c(x+1)], dat)
      cbind.data.frame(dat, setNames(res, paste0(names(res), "_diff")))
        group time A_1 A_3 B_1 B_3 C_1 C_3 A_1_diff B_1_diff C_1_diff
      1     1  100   7   5   7   3   5   3        2        4        2
      2     1  200   8   4   5   6   1   2        4       -1       -1
      3     1  300   5   6   8   9   2   1       -1       -1        1
      4     1  400   3   5   7   8   2   1       -2       -1        1
      5     2  100   3   5   7   6   3   2       -2        1        1
      6     2  200   4   5   6   0   1   4       -1        6       -3
      7     2  300   3   3   4   5   3   2        0       -1        1
      8     2  400   6   5   3   1   3   7        1        2       -4
      

      【讨论】:

        猜你喜欢
        • 2023-01-29
        • 2019-05-04
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-04-01
        • 2022-01-22
        • 1970-01-01
        • 2015-03-20
        相关资源
        最近更新 更多