如何向每个组添加行并分配值

Tar*_*Jae 5 r dplyr tibble

我有这个小题:

\n
library(tibble)\nlibrary(dplyr)\n\ndf <- tibble(id = c("one", "two", "three"),\n             A = c(1,2,3), \n             B = c(4,5,6))\n\n  id        A     B\n  <chr> <dbl> <dbl>\n1 one       1     4\n2 two       2     5\n3 three     3     6\n
Run Code Online (Sandbox Code Playgroud)\n

我想向每个组添加一行,并为新列分配值,但使用一个函数(这里每个组中的新行应该= USINGA=4 B列的第一个组值->所需的输出B first(B)

\n
id        A     B\n<chr> <dbl> <dbl>\n1 one       1     4\n2 one       4     4\n3 three     3     6\n4 three     4     6\n5 two       2     5\n6 two       4     5\n
Run Code Online (Sandbox Code Playgroud)\n

到目前为止我已经尝试过:

\n

如果我在未分组的小标题中添加一行add_row-> 这很完美

\n
df %>% \n  add_row(A=4, B=4)\n\n  id        A     B\n  <chr> <dbl> <dbl>\n1 one       1     4\n2 two       2     5\n3 three     3     6\n4 NA        4     4\n
Run Code Online (Sandbox Code Playgroud)\n

add_row如果我尝试在分组的 tibble 中使用->这不起作用

\n
df %>% \n  group_by(id) %>%\n  add_row(A=4, B=4)\n\nError: Can\'t add rows to grouped data frames.\nRun `rlang::last_error()` to see where the error occurred.\n
Run Code Online (Sandbox Code Playgroud)\n

根据这篇文章Add row in every group using dplyr and add_row()我们可以使用group_modify-> 这效果很好

\n
df %>% \n  group_by(id) %>% \n  group_modify(~ add_row(A=4, B=4, .x))\n\n  id        A     B\n  <chr> <dbl> <dbl>\n1 one       1     4\n2 one       4     4\n3 three     3     6\n4 three     4     4\n5 two       2     5\n6 two       4     4\n
Run Code Online (Sandbox Code Playgroud)\n

我想将列B的第一个值分配给列B(或者它可以是任何函数min(B)max(B))->这不起作用:

\n
df %>% \n  group_by(id) %>% \n  group_modify(~ add_row(A=4, B=first(B), .x))\n\nError in h(simpleError(msg, call)) : \n  Fehler bei der Auswertung des Argumentes \'x\' bei der Methodenauswahl f\xc3\xbcr Funktion \'first\': object \'B\' not found\n
Run Code Online (Sandbox Code Playgroud)\n

jpd*_*o17 5

library(tidyverse)\n\ndf <- tibble(id = c("one", "two", "three"),\n             A = c(1,2,3), \n             B = c(4,5,6))\n\ndf %>% \n    group_by(id) %>% \n    summarise(add_row(cur_data(), A = 4, B = first(cur_data()$B)))\n#> `summarise()` has grouped output by \'id\'. You can override using the `.groups` argument.\n#> # A tibble: 6 \xc3\x97 3\n#> # Groups:   id [3]\n#>   id        A     B\n#>   <chr> <dbl> <dbl>\n#> 1 one       1     4\n#> 2 one       4     4\n#> 3 three     3     6\n#> 4 three     4     6\n#> 5 two       2     5\n#> 6 two       4     5\n
Run Code Online (Sandbox Code Playgroud)\n

或者

\n
df %>% \n    group_by(id) %>% \n    group_split() %>% \n    map_dfr(~ add_row(.,id = first(.$id),  A = 4, B = first(.$B)))\n#> # A tibble: 6 \xc3\x97 3\n#>   id        A     B\n#>   <chr> <dbl> <dbl>\n#> 1 one       1     4\n#> 2 one       4     4\n#> 3 three     3     6\n#> 4 three     4     6\n#> 5 two       2     5\n#> 6 two       4     5\n
Run Code Online (Sandbox Code Playgroud)\n

由reprex 包于 2022 年 1 月 2 日创建(v2.0.1)

\n


Maë*_*aël 4

根据函数的文档group_modify,如果使用公式,则必须使用“.或来引用给定组.x的行子集;” .tbl这就是你在函数.x内部使用的原因add_row。为了完全一致,您还必须在first函数内执行此操作。

df %>% 
  group_by(id) %>% 
  group_modify(~ add_row(A=4, B=first(.x$B), .x))

# A tibble: 6 x 3
# Groups:   id [3]
  id        A     B
  <chr> <dbl> <dbl>
1 one       1     4
2 one       4     4
3 three     3     6
4 three     4     6
5 two       2     5
6 two       4     5
Run Code Online (Sandbox Code Playgroud)

使用first(.$B)orfirst(df$B)将提供相同的结果。