没有值列的情况下,pivot_wider

时间:2020-03-04 22:48:50

标签: r tidyverse

我正在尝试从长到宽重塑数据集。以下代码有效,但我很好奇是否有一种方法不提供值列,而仍使用pivot_wider。在下面的示例中,我必须创建一个临时列“ val”以使用pivot_wider,但是有没有办法我可以做到这一点?

a <- data.frame(name = c("sam", "rob", "tom"),
                 type = c("a", "b", "c"))
a
  name type
1  sam    a
2  rob    b
3  tom    c

我想将其转换为以下内容。

name      a     b     c
1 sam       1     0     0
2 rob       0     1     0
3 tom       0     0     1 

这可以通过以下代码完成,但是我可以在不创建“ val”列的情况下(仍然使用tidyverse语言)来做到这一点吗?

a <- data.frame(name = c("sam", "rob", "tom"),
                type = c("a", "b", "c"), 
                val = rep(1, 3)) %>%
  pivot_wider(names_from = type, values_from = val, values_fill = list(val = 0))

3 个答案:

答案 0 :(得分:6)

您可以使用values_fn参数分配1,并使用values_fill分配0:

library(tidyr)

pivot_wider(a, names_from = type, values_from = type, values_fn = list(type = ~1), values_fill = list(type = 0))

# A tibble: 3 x 4
  name      a     b     c
  <fct> <dbl> <dbl> <dbl>
1 sam       1     0     0
2 rob       0     1     0
3 tom       0     0     1

答案 1 :(得分:6)

我们可以mutate的列为1s,并在pivot_wider中使用它

library(dplyr)
library(tidyr)
a %>%
     mutate(n = 1) %>% 
     pivot_wider(names_from = type, values_from = n, values_fill = list(n = 0))
# A tibble: 3 x 4
#  name      a     b     c
#  <fct> <dbl> <dbl> <dbl>
#1 sam       1     0     0
#2 rob       0     1     0
#3 tom       0     0     1

base R中,会更容易。

table(a)

答案 2 :(得分:6)

reshape2::dcast或蓬勃发展的data.table::dcast上学,让您通过指定聚合函数来做到这一点:

reshape2::dcast(a, name ~ type, fun.aggregate = length)
#   name a b c
# 1  rob 0 1 0
# 2  sam 1 0 0
# 3  tom 0 0 1

data.table::dcast(setDT(a), name ~ type, fun.aggregate = length)
#    name a b c
# 1:  rob 0 1 0
# 2:  sam 1 0 0
# 3:  tom 0 0 1