如何在tidyverse函数中正确求值含空格的变量
问题说明
- 自定义函数中使用带空格的变量名时触发运行错误,已知带空格命名不属于良好编码习惯
- 调用的rstatix包统计函数基于tidyverse非标准计算(NSE)机制,使用
sym()配合!!运算符可正常读取无空格列,但变量名包含空格时无法找到适配dplyr非标准计算的实现方式 - 此前尝试加判断逻辑:当quantvar参数包含空格时,为其两侧包裹反引号,该写法可正确生成formula对象,满足所有公式传参类统计检验的要求,但调用基于tidyverse NSE的
shapiro_test()执行夏皮罗检验时报错 - 需要找到兼容两种传参逻辑的写法,让代码可灵活适配带/不带空格的变量名
- 临时替代方案为使用非NSE函数,或直接修改原始数据列名
错误原因
手动给带空格变量名包裹反引号的操作仅适用于公式构造场景:sym()函数本身支持直接传入带空格的原始列名生成合法的R符号,不需要额外添加反引号。提前给字符串加反引号后,sym()会把反引号也识别为列名的组成部分,最终会去查找名称为`var space`的不存在的列,触发子集报错。
修正方案
不需要提前判断变量名是否含空格、修改原始传入的字符串,两个传参场景分别适配即可:
- 构造公式时,统一给所有变量名两侧包裹反引号,该写法对带空格、无空格的列名均生效
- 调用tidy系NSE函数时,直接使用原始传入的列名字符串生成symbol,不做额外转义
library(rstatix) library(glue) library(tidyverse) make_kruskal_test <- function(data, quantvar, groupvar) { # 构造公式时统一用反引号包裹变量,兼容所有合法列名 formula_expression <- formula(glue("`{quantvar}` ~ `{groupvar}`")) bartlett <- bartlett.test(formula_expression, data) %>% print() # NSE场景直接用原始列名生成符号,无需额外加反引号 shapiro <- shapiro_test(data, !!sym(quantvar)) %>% print() } # 测试数据 data <- tibble("var_snake" = c(1:5), "var space" = 2, "group_var" = c(3, 3, 4, 4, 4)) # 无空格列名测试 make_kruskal_test(data, "var_snake", "group_var") # 带空格列名测试 make_kruskal_test(data, "var space", "group_var")
注:长期来看更稳妥的方案仍是提前将数据列名修改为无空格的规范命名,可规避绝大多数非标准计算相关的兼容问题。
内容的提问来源于stack exchange,提问作者Minh-Anh Huynh
相关产品推荐
相关产品推荐

