前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >R tips:dplyr编程

R tips:dplyr编程

作者头像
生信菜鸟团
发布2020-07-02 11:33:16
1.2K0
发布2020-07-02 11:33:16
举报
文章被收录于专栏:生信菜鸟团

dplyr的函数由于使用tidy evaluation(R中的一种非标准执行(NSE)实现方式)的方法,可以使得其具有更好的易用性:变量不需要绝对引用和引号包裹。

根据使用的NSE的类别不同,dplyr的函数可以分为两类:

  • data masking:arrange(), count(), filter(), group_by(), mutate(), summarise(),data masking可以使得使用用户数据变量像使用环境变量一样易用。
  • tidy selection:across(), relocate(), rename(), select(), pull() ,使得可以很方便的根据位置、名称、类别去选择数据变量。

环境变量与数据变量

环境变量是存在于环境中的变量,一般通过"<-"来创建。

数据变量是一种存在于数据框(data.frame)的变量,常常是来源于数据文件。比如mtcars中mpg、cyl等等。

根据所用的NSE的类别,需要区别对待dplyr函数的编程。

Data masking

如果想要操作的数据变量名称来源于环境变量,那么使用特殊的指代词.data来完成。

代码语言:javascript
复制
library(tidyverse)
# 常规使用是会报错的
grp_var <- "vs"
mtcars %>% group_by(grp_var) %>% summarise(mean_disp = mean(disp))
#Error: Column `grp_var` is unknown

# 使用.data即可
mtcars %>% group_by(.data[[grp_var]]) %>% summarise(mean_disp = mean(disp))
# A tibble: 2 x 2
#     vs mean_disp
#  <dbl>     <dbl>
#1     0      307.
#2     1      132.

如果想要操作的数据变量来源于函数参数(指的一个环境变量上存在一个promise),那么使用{{}}包裹。

一个函数在调用时,其参数存在一个promise。原因在于R的参数是 lazily evaluated,也就是说直到使用此参数前,这些参数并没有实际值(实际值也就是实参),而只有一个获取其实际值的方法(promise)。

代码语言:javascript
复制
# 使用{{}}包裹
summarise_grp <- function(data, grp){
  data %>% group_by({{grp}}) %>% summarise(mean_disp = mean(disp))
}
mtcars %>% summarise_grp(vs)
# # A tibble: 2 x 2
# vs mean_disp
# <dbl>     <dbl>
# 1     0      307.
# 2     1      132.

Tidy selection

如果想要操作的数据变量名称来源于环境变量,那么使用all_of或者any_of。

代码语言:javascript
复制
grp_var <- c("vs","cyl")
mtcars %>% select(all_of(grp_var)) %>% head
# vs cyl
# Mazda RX4          0   6
# Mazda RX4 Wag      0   6
# Datsun 710         1   4
# Hornet 4 Drive     1   6
# Hornet Sportabout  0   8
# Valiant            1   6
mtcars %>% select(!all_of(grp_var)) %>% head
# mpg disp  hp drat    wt  qsec am gear carb
# Mazda RX4         21.0  160 110 3.90 2.620 16.46  1    4    4
# Mazda RX4 Wag     21.0  160 110 3.90 2.875 17.02  1    4    4
# Datsun 710        22.8  108  93 3.85 2.320 18.61  1    4    1
# Hornet 4 Drive    21.4  258 110 3.08 3.215 19.44  0    3    1
# Hornet Sportabout 18.7  360 175 3.15 3.440 17.02  0    3    2
# Valiant           18.1  225 105 2.76 3.460 20.22  0    3    1

all_of和any_of的区别在于,如果不是所有的变量都存在于数据框中,那么all_of会报错,any_of不会报错,按需使用。

如果想要操作的数据变量来源于函数参数,那么使用{{}}包裹。

代码语言:javascript
复制
map(grp_var, function(x){
  mtcars %>% select({{x}}) %>% head
})
# [[1]]
# vs
# Mazda RX4          0
# Mazda RX4 Wag      0
# Datsun 710         1
# Hornet 4 Drive     1
# Hornet Sportabout  0
# Valiant            1
# 
# [[2]]
# cyl
# Mazda RX4           6
# Mazda RX4 Wag       6
# Datsun 710          4
# Hornet 4 Drive      6
# Hornet Sportabout   8
# Valiant             6

参考资料

Programming with dplyr :https://dplyr.tidyverse.org/articles/programming.html

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-06-30,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 生信菜鸟团 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • Data masking
  • Tidy selection
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档