R语言:bi_class函数传递列名参数失败,如何让R识别变量?
解决R语言
bi_class函数传递列名参数的问题 问题描述
在自定义create_sf_func()函数时,尝试将字符串形式的列名参数传递给bi_class函数,用于生成双变量地图的三分位数分组阈值,但R无法正确识别该变量,触发错误:
Error in if (var %in% names(.data) == FALSE) { : the condition has length > 1
原代码如下:
create_sf_func <- function(yrqrt, variable) { df <- bi_class(df2, x = QRT_TESTS_PER1K, y = df2[[variable]], style = "quantile", dim = 3) df_filtered <- sf::st_as_sf(df %>% filter(YEAR_QRT == yrqrt) %>% right_join(all_fips, by=c("FIPS5"="FIPS5")) %>% mutate(geometry = fips_geometry(FIPS5)) %>% filter(FIPS5<60), crs = 4269) %>% shift_geometry() return(df_filtered) } df_cases2022Q2 <- create_sf_func("2022Q2", "CASES_PER100K")
错误原因
bi_class函数的x、y参数需要的是数据框中的变量名(symbol类型),而非直接传入列值向量。原代码中df2[[variable]]直接提取了列的数值向量,导致函数内部的变量存在性检查逻辑出错:它会把整个向量当作待检查的变量名,从而返回长度远大于1的逻辑向量,而if条件只能接受长度为1的判断值,因此触发报错。
解决方案
提供两种适配不同调用习惯的修改方式:
方式1:传递裸变量名(推荐)
利用R的非标准求值(NSE)特性,用{{ }}(大括号运算符)直接引用函数参数,自动处理变量名转换:
create_sf_func <- function(yrqrt, variable) { # 使用{{ }}引用参数,自动将传入的变量名转换为bi_class需要的格式 df <- bi_class(df2, x = QRT_TESTS_PER1K, y = {{ variable }}, style = "quantile", dim = 3) df_filtered <- sf::st_as_sf(df %>% filter(YEAR_QRT == yrqrt) %>% right_join(all_fips, by=c("FIPS5"="FIPS5")) %>% mutate(geometry = fips_geometry(FIPS5)) %>% filter(FIPS5<60), crs = 4269) %>% shift_geometry() return(df_filtered) } # 调用时直接传入裸变量名,无需加引号 df_cases2022Q2 <- create_sf_func("2022Q2", CASES_PER100K)
方式2:保持字符串列名调用
如果需要保留原调用时传递字符串列名的习惯,可先将字符串转为symbol类型,再用!!(注入运算符)传入bi_class:
create_sf_func <- function(yrqrt, variable) { # 将字符串列名转换为symbol,再用!!注入到bi_class中 var_sym <- rlang::sym(variable) df <- bi_class(df2, x = QRT_TESTS_PER1K, y = !!var_sym, style = "quantile", dim = 3) df_filtered <- sf::st_as_sf(df %>% filter(YEAR_QRT == yrqrt) %>% right_join(all_fips, by=c("FIPS5"="FIPS5")) %>% mutate(geometry = fips_geometry(FIPS5)) %>% filter(FIPS5<60), crs = 4269) %>% shift_geometry() return(df_filtered) } # 保持原调用方式,传递字符串列名 df_cases2022Q2 <- create_sf_func("2022Q2", "CASES_PER100K")
内容的提问来源于stack exchange,提问作者Quinterpret
相关产品推荐
相关产品推荐

