dplyr + group_by并避免按字母顺序排序

Mar*_*lla 5 r dplyr

我有以下数据:

    data <- structure(list(user = c(1234L, 1234L, 1234L, 1234L, 1234L, 1234L, 
1234L, 1234L, 1234L, 1234L, 1234L, 4758L, 4758L, 9584L, 9584L, 
9584L, 9584L, 9584L, 9584L), time = c(1L, 2L, 3L, 4L, 5L, 6L, 
7L, 8L, 9L, 10L, 11L, 5L, 6L, 1L, 2L, 3L, 4L, 5L, 6L), fruit = structure(c(1L, 
6L, 1L, 1L, 6L, 5L, 5L, 3L, 4L, 1L, 2L, 4L, 2L, 1L, 6L, 5L, 5L, 
3L, 2L), .Label = c("apple", "banana", "lemon", "lime", "orange", 
"pear"), class = "factor"), count = c(1L, 1L, 1L, 1L, 1L, 1L, 
1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L), cum_sum = c(1L, 
2L, 3L, 4L, 5L, 6L, 7L, 8L, 9L, 10L, 11L, 1L, 2L, 1L, 2L, 3L, 
4L, 5L, 6L)), .Names = c("user", "time", "fruit", "count", "cum_sum"
), row.names = c(NA, -19L), class = "data.frame")
Run Code Online (Sandbox Code Playgroud)

对于这一组中的每个用户,我想看一下随着时间推移的水果序列.但是,一些水果被"背靠背"列出.

   user time  fruit count cum_sum
1  1234    1  apple     1  1
2  1234    2   pear     1  2
3  1234    3  apple     1  3
4  1234    4  apple     1  4
5  1234    5   pear     1  5
6  1234    6 orange     1  6
7  1234    7 orange     1  7
Run Code Online (Sandbox Code Playgroud)

我正在寻找的更多是用户通过独特水果的时间序列.

问题是,如果我按用户和水果分组然后总结,dplyr会按字母顺序自动排序水果:

data %>% 
    group_by(user, fruit) %>%
    summarise(temp_var=1) %>%
    mutate(cum_sum = cumsum(temp_var))
Run Code Online (Sandbox Code Playgroud)

我真正想要的是,对于上面的用户1234(例如),按时间序列的顺序列出水果,但删除任何重复.所以我们看到苹果>梨>苹果>苹果>梨>橙>橙,我们只会看到苹果>梨>苹果>梨>橙

Dav*_*urg 6

因此,使用CRAN上rleid最新data.table版本的功能,我们可以做到(虽然不确定您确切的所需输出)

library(data.table) ## v >= 1.9.6
res <- setDT(data)[, .(fruit = fruit[1L]), by = .(user, indx = rleid(fruit))
                    ][, cum_sum := seq_len(.N), by = user
                      ][, indx := NULL]
res
#     user  fruit cum_sum
#  1: 1234  apple       1
#  2: 1234   pear       2
#  3: 1234  apple       3
#  4: 1234   pear       4
#  5: 1234 orange       5
#  6: 1234  lemon       6
#  7: 1234   lime       7
#  8: 1234  apple       8
#  9: 1234 banana       9
# 10: 4758   lime       1
# 11: 4758 banana       2
# 12: 9584  apple       1
# 13: 9584   pear       2
# 14: 9584 orange       3
# 15: 9584  lemon       4
# 16: 9584 banana       5
Run Code Online (Sandbox Code Playgroud)


Pie*_*une 5

根据您的示例,这可能会有所帮助:

data %>%
group_by(user) %>%
filter(c(T,fruit[-1L] != fruit[-length(fruit)])) %>%
mutate(cum_sum = cumsum(count),
     time = seq_along(count))
# Source: local data frame [16 x 5]
# Groups: user
#
#    user time  fruit count cum_sum
# 1  1234    1  apple     1       1
# 2  1234    2   pear     1       2
# 3  1234    3  apple     1       3
# 4  1234    4   pear     1       4
# 5  1234    5 orange     1       5
# 6  1234    6  lemon     1       6
# 7  1234    7   lime     1       7
# 8  1234    8  apple     1       8
# 9  1234    9 banana     1       9
# 10 4758    1   lime     1       1
# 11 4758    2 banana     1       2
# 12 9584    1  apple     1       1
# 13 9584    2   pear     1       2
# 14 9584    3 orange     1       3
# 15 9584    4  lemon     1       4
# 16 9584    5 banana     1       5
Run Code Online (Sandbox Code Playgroud)