Pivot_wider 引入 NA

Ale*_*lex 5 r dplyr

我正在为一个项目进行数据管理,我认为从长格式到宽格式的基本重塑遇到了困难。

数据看起来像这样:

df <- structure(list(ID = c(1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2), 
               Time = c(1, 1, 1, 1, 2, 2, 2, 2, 3, 1, 1, 1, 1, 2, 2), 
               Type = c("A", "B", "C", "D", "A", "B","C", "D", "A", "A", "B", "C", "D", "A", "B"),
               Value = c(100, NA, 40, 123, 95, NA, 45, 1234, 100, 70, NA, 50, 12345, 75, NA)), 
               row.names = c(NA, 15L), class = "data.frame")
Run Code Online (Sandbox Code Playgroud)

根据之前的 Stackoverflow 答案,我尝试使用像这样的数据透视更广泛:

df.wide <- df %>%
  group_by(ID, Type) %>%
  mutate(row = row_number()) %>%
  pivot_wider(names_from = Type, values_from = Value)
Run Code Online (Sandbox Code Playgroud)

然而,这会返回一个数据帧,其中每个 ID 的 max(Time) 处的 NA 值如下所示:

# A tibble: 5 x 7
     ID  Time   row     A     B     C     D
  <dbl> <dbl> <int> <dbl> <dbl> <dbl> <dbl>
1     1     1     1   100    NA    40   123
2     1     2     2    95    NA    45  1234
3     1     3     3   100    NA    NA    NA
4     2     1     1    70    NA    50 12345
5     2     2     2    75    NA    NA    NA
Run Code Online (Sandbox Code Playgroud)

我究竟做错了什么?我的谷歌和 Stackoverflow-fu 无法帮助我。

Mar*_*ark 3

-edpivot_wider()数据有两种 NA:

\n
    \n
  1. 数据集中已有的 NA,以及
  2. \n
  3. 这些是通过将数据旋转得更宽而引入的,在给定行和列的数据中不存在值的地方。
  4. \n
\n

要摆脱类型 1,您可以使用df |> replace_na(list(Value = 0)).
\n要删除类型 2,您可以使用参数values_fill = 0(或者如果您只想从特定列中删除它们,那么您可以命名该列,例如values_fill = list(Value = 0)

\n

要删除它们,您可以执行以下操作:

\n
library(tidyverse)\n\ndf |>\n  replace_na(list(Value = 0)) |>\n  pivot_wider(names_from = Type, values_from = Value, values_fill = 0)\n
Run Code Online (Sandbox Code Playgroud)\n

输出:

\n
# A tibble: 5 \xc3\x97 6\n     ID  Time     A     B     C     D\n  <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>\n1     1     1   100     0    40   123\n2     1     2    95     0    45  1234\n3     1     3   100     0     0     0\n4     2     1    70     0    50 12345\n5     2     2    75     0     0     0\n
Run Code Online (Sandbox Code Playgroud)\n

或者,您可以在不使用values_fill的情况下将数据旋转得更宽,然后使用replace_na(list(A = 0, B = 0, C = 0, D = 0)),但上面的选项更简洁。

\n