应用函数和top_n不能很好地结合起来。

问题描述 投票:0回答:1

我有一个简单的数据框架 df 在R中。

year, var1, var2, var3
1990, 23, 1, 133
1991, 25, 3, 120
1992, 28, 2, 110
...

数据有几百行。

我想为var1, var2, var3选择前10位的值,使用的是 apply()top_n() 在R中,像这样。

df %>%
 select(var1, var2, var3) %>%
 apply(2, top_n(10), na.rm = TRUE)

但我得到了错误信息Error in UseMethod("tbl_vars"): no applicable method for "tbl_vars" applied to an object of class "c('double', 'numeric')"

我以为... apply 可以帮助我避免使用for循环来逐个变量获取前10个值,但我没能做到。

这似乎是个简单的问题,但我在网上没有找到好的答案。有什么想法吗?

r dplyr apply
1个回答
0
投票

top_n 期待一个data.frame作为输入,而当我们使用 apply, MARGIN = 2,它是在每一列上循环,即 a vector

library(purrr)
library(dplyr)
map_dfc(c('var1', 'var2', 'var3'), ~ df %>%
                                 select(.x) %>%
                                 top_n(10) %>%
                                  slice(seq_len(10)))

同时,根据 ?top_n替换为 slice_max/slice_min

map(c('var1', 'var2', 'var3'), ~ df %>%
                                 select(.x) %>%
                                 slice_max(!! rlang::sym(.x), n = 10)) 

使用一个可重复的例子 iris

map_dfc(names(iris)[1:4], ~
          iris %>% 
              select(.x) %>% 
              top_n(10) %>% 
              slice(seq_len(10)))

map(names(iris)[1:4], ~
          iris %>% 
              select(.x) %>% 
              slice_max(!! rlang::sym(.x), n = 10))

或与 summariseacrosssort

library(tidyr)
df %>%
     summarise(across(starts_with('var'), ~ 
       list(head(sort(., decreasing = TRUE), 10)))) %>%
     unnest(c(everything())

0
投票

通常情况下,最好是长格式的数据,这样可以很方便地进行此类操作。

你可以使用 pivot_longer 为了获得长格式的数据,那么对于每一列,你可以根据列中的值选择前10个值。

library(dplyr)
df %>% tidyr::pivot_longer(cols = -year) %>% group_by(name) %>%  top_n(10, value)
© www.soinside.com 2019 - 2024. All rights reserved.