繁体   English   中英

r tidyverse spread()使用多个键值对而不是折叠行

[英]r tidyverse spread() using multiple key value pairs not collapsing rows

我试图传播()几个键/值对,但公共值列不会崩溃。 我认为它可能与某些先前的处理有关,或者更可能是我不知道正确的方式来传播两个或更多的键/值对以获得我期望的结果。

我从这个数据集开始:

library(tidyverse)

df <- tibble(order = 1:7,
             line_1 = c(23,8,21,45,68,31,24),
             line_2 = c(63,25,25,24,48,24,63),
             line_3 = c(62,12,10,56,67,25,35))

有两个预扩展步骤来定义在以下gather()函数中创建的“count”值的顺序。 这是使用行号定义“count”变量的原始顺序的第一个预扩展步骤:

ntrl <- df %>%
           gather(line_1,
                  line_2,
                  line_3,
                  key = "sector",
                  value = "count") %>%
           group_by(order) %>%
           mutate(sector_ord = row_number()) %>%
           arrange(order,
                   sector)

这是定义“count”变量的数字顺序的第二个预扩展步骤:

ord <- ntrl %>%
            arrange(order,
                    count) %>%
            group_by(order) %>%
            mutate(num_ord = paste0("ord_",
                                    row_number(),
                                    sep=""))

然后最后我一直使用的传播代码:

wide <- ord %>%
            group_by(order) %>%
            spread(key = sector,
                   value = count) %>%
            spread(key = num_ord,
                   value = sector_ord)

我得到的是这个:

    order   line_1  line_2  line_3  ord_1   ord_2   ord_3                           
1   1       23      NA      NA      1       NA      NA
2   1       NA      63      NA      NA      NA      2
3   1       NA      NA      62      NA      3       NA
4   2       8       NA      NA      1       NA      NA
5   2       NA      25      NA      NA      NA      2
6   2       NA      NA      12      NA      3       NA
7   3       21      NA      NA      NA      1       NA
8   3       NA      25      NA      NA      NA      2
9   3       NA      NA      10      3       NA      NA
... and so on thru 21 lines accounting for all 7 "order" lines

我期待的行为是“order”列将在所有具有相同“order”值的行中折叠,以提供以下内容:

    order   line_1  line_2  line_3  ord_1   ord_2   ord_3                           
1   1       23      63      62      1       3       2
2   2       8       25      12      1       3       2
3   3       21      25      10      2       3       1
4   4       45      24      56      2       1       3
... and so on, I think that paints the picture

我已经回顾了有关使用重复标识符传播和使用行号索引的问题和答案,但这没有帮助。

我认为它与双重传播有关,但我无法弄清楚如何做到这一点。

谢谢你的帮助。

使用tidyverse启动你的df解决方案。 关键是使用summarise_all(funs(.[which(!is.na(.))]))为每列选择唯一的非NA值。

library(tidyverse)

df2 <- df %>%
  gather(Lines, Value, -order) %>%
  group_by(order) %>%
  mutate(Rank = dense_rank(Value), 
         RankOrder = paste0("ord_", row_number())) %>%
  spread(Lines, Value) %>%
  spread(RankOrder, Rank) %>%
  summarise_all(funs(.[which(!is.na(.))]))
df2
# A tibble: 7 x 7
  order line_1 line_2 line_3 ord_1 ord_2 ord_3
  <int>  <dbl>  <dbl>  <dbl> <int> <int> <int>
1     1     23     63     62     1     3     2
2     2      8     25     12     1     3     2
3     3     21     25     10     2     3     1
4     4     45     24     56     2     1     3
5     5     68     48     67     3     1     2
6     6     31     24     25     3     1     2
7     7     24     63     35     1     3     2

df开始:

df %>% 
    gather(headers, line, -order) %>% 
    separate(headers, into = c('dummy', 'rn')) %>% 
    select(-dummy) %>% 
    group_by(order) %>% 
    mutate(ord = rank(line, ties.method='first')) %>% 
    {data.table::dcast(setDT(.), order ~ rn, value.var = c("line", "ord"))}

#   order line_1 line_2 line_3 ord_1 ord_2 ord_3
#1:     1     23     63     62     1     3     2
#2:     2      8     25     12     1     3     2
#3:     3     21     25     10     2     3     1
#4:     4     45     24     56     2     1     3
#5:     5     68     48     67     3     1     2
#6:     6     31     24     25     3     1     2
#7:     7     24     63     35     1     3     2

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM