dplyr - 如何过滤掉销售额总和更高的前n组?

3
我正在使用R上的dplyr,并尝试筛选包含交易数据的表格。我感兴趣的列是“国家”和“销售额”。
由于探索目的,我要分析销售额排名前五的国家,但我有很多国家。
这里的问题是,如果我进行一些分组,它对我是不起作用的,因为我需要所有行以进行进一步的分析(交易数据)。
我尝试了以下内容:
trans_merch_df %>% group_by(COUNTRY) %>% top_n(n = 5, wt = NET_SLS_AMT)

但它完全错误。

假设我有这个:

trans_merch_df <- tibble::tribble(~COUNTRY, ~SALE,
                                  'POR',     14,
                                  'POR',     1,
                                  'DEU',     4,
                                  'DEU',     6,
                                  'POL',     8,
                                  'ITA',     1,
                                  'ITA',     1,
                                  'ITA',     1,
                                  'SPA',     1,
                                  'NOR',     50,
                                  'NOR',     10,
                                  'SWE',     42,
                                  'SWE',     1)


我期望的结果是:
COUNTRY   SALE
POR       14
POR       1
DEU       4
DEU       6
POL       8
NOR       50
NOR       10
SWE       42
SWE       1

由于ITA和SPA的销售额不在前五名,因此需要加强推广。

提前谢谢您的帮助。

祝好!


1
为了理解你的方法出了什么问题,每当你使用 group_by 时,就像你有一个单独的小数据框架用于每个组,每个组都会发生一切然后重新组合。当你使用 group_by() %>% top_n() 时,你是在每个组内提取前几行,而不是前5个组。 - Gregor Thomas
2个回答

6

另一个 dplyr 的可能性是:

df %>%
 add_count(COUNTRY, wt = SALE) %>%
 mutate(n = dense_rank(desc(n))) %>%
 filter(n %in% 1:5) %>%
 select(-n)


  COUNTRY  SALE
  <chr>   <int>
1 POR        14
2 POR         1
3 DEU         4
4 DEU         6
5 POL         8
6 NOR        50
7 NOR        10
8 SWE        42
9 SWE         1

甚至更加简洁:
df %>%
 add_count(COUNTRY, wt = SALE) %>%
 filter(dense_rank(desc(n)) %in% 1:5) %>%
 select(-n)

完美。第一个非常方便,因为我可以保留排名,这在以后可能会有用。我是这样做的: trans_merch_df %>% add_count(COUNTRY, wt = NET_SLS_AMT) %>% mutate(rank = dense_rank(desc(n))) %>% filter(rank %in% 1:10) %>% select(-n) - spcvalente

1
这是一种使用join的方法。
library(dplyr)
trans_merch_df %>% 
  # First figure the top 5 countries' by total sales, equiv to 
  #    group_by(COUNTRY) %>% summarize(n = sum(NET_SLS_AMT)
  count(COUNTRY, wt = SALE, sort = T) %>%    
  top_n(n = 5, wt = n) %>%

  # now add back orig data for those countries
  left_join(trans_merch_df)

#Joining, by = "COUNTRY"
## A tibble: 9 x 3
#  COUNTRY     n  SALE
#  <chr>   <int> <int>
#1 NOR        60    50
#2 NOR        60    10
#3 SWE        43    42
#4 SWE        43     1
#5 POR        15    14
#6 POR        15     1
#7 DEU        10     4
#8 DEU        10     6
#9 POL         8     8

谢谢!它可以工作,但那是一种类似于SQL的方法,我期望得到更多“dplyr-y”或“R-y”的东西 :) 不过了解这种方法还是很好的。谢谢! - spcvalente

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接