如何实现不区分大小写的R裸表达式向量存在性检查函数
大小写不敏感的裸表达式向量检查函数实现
问题背景
需要实现一个函数,既能检查裸表达式(如a或c(a,B))是否存在于目标向量中,又不受输入数据的大小写影响。此前两种方案各有缺陷:
tidyselect::eval_select()支持复杂表达式,但严格区分大小写,大写符号会因环境中无对应变量报错- 单纯
rlang::enexprs()能兼容大小写,但无法正确解析c(a,b,z)这类组合表达式,返回错误结果
解决方案
以下函数通过解析表达式结构+统一大小写处理,同时满足两种场景需求:
library(rlang) library(purrr) is_abc <- function(expr, target) { # 解析输入的裸表达式 parsed_expr <- enexpr(expr) # 处理c()组合表达式,提取内部参数;单个表达式直接处理 expr_syms <- if (is_call(parsed_expr, "c")) { call_args(parsed_expr) } else { list(parsed_expr) } # 将表达式符号转为字符串并统一为小写 expr_strs <- tolower(map_chr(expr_syms, as.character)) # 目标向量转为小写,实现大小写不敏感匹配 target_lower <- tolower(as.character(target)) # 检查每个目标元素是否存在于表达式集合中 target_lower %in% expr_strs }
测试示例
# 测试c()组合表达式场景 is_abc(c(a,B), c(a, B, z)) # 输出:[1] TRUE TRUE FALSE # 测试单个表达式场景 is_abc(A, c(a, b, A)) # 输出:[1] TRUE TRUE TRUE
方案说明
- 表达式解析:用
rlang::enexpr()捕获裸表达式,通过is_call()判断是否为c()组合调用,再用call_args()提取内部参数,确保支持单个或多个表达式的输入 - 大小写统一:将表达式符号和目标向量全部转为小写,彻底消除大小写差异的影响
- 存在性检查:用
%in%实现向量级别的存在性判断,返回与目标向量长度一致的逻辑结果
内容的提问来源于stack exchange,提问作者arangaca
相关产品推荐
相关产品推荐

