如何在tidyr的gather函数中使用变量设置key参数?
解决tidyr::gather中用变量设置key/value参数的问题
错误原因
你遇到的ensym2()报错,是因为gather的key/value参数默认只接受**列名字面量(符号)**或直接的字符串字面量,无法直接识别字符串变量。同时你的代码还存在参数逻辑混淆的问题,需要先理清需求再调整。
解决方案
方案1:用tidyeval语法适配gather函数
通过rlang::sym()将字符串变量转为符号,再用!!强制解析变量,同时修正参数逻辑并优化变量命名:
library(tidyr) library(dplyr) library(rlang) path = "C:/Users/lukas/Documents/Projekt/Data/" files <- list.files(path = path, pattern = "*.csv") dane <- list() for (file in files){ # 可选:去掉文件名的.csv后缀,让列名更简洁 temp_name <- tools::file_path_sans_ext(file) # 避免覆盖循环变量file,改用file_data存储处理后的数据 file_data <- tibble(read.csv(paste0(path, file))) %>% # 假设需求:将country外的列转为year(key列),值列用文件名命名 gather(key = "year", value = !!sym(temp_name), -country) dane <- append(dane, list(file_data)) }
如果你的需求是key列用文件名命名,则调整gather的参数:
gather(key = !!sym(temp_name), value = "year", -country)
方案2:改用pivot_longer(推荐)
tidyr官方已推荐用pivot_longer替代旧的gather函数,它的names_to和values_to参数直接支持字符串变量,无需额外解析,语法更清晰:
library(tidyr) library(dplyr) path = "C:/Users/lukas/Documents/Projekt/Data/" files <- list.files(path = path, pattern = "*.csv") dane <- list() for (file in files){ temp_name <- tools::file_path_sans_ext(file) file_data <- tibble(read.csv(paste0(path, file))) %>% pivot_longer(cols = -country, names_to = "year", values_to = temp_name) dane <- append(dane, list(file_data)) }
额外优化提示
- 用
paste0()代替paste(..., sep=""),代码更简洁; - 循环中避免覆盖迭代变量
file,改用新变量名存储处理后的数据; - 用
tools::file_path_sans_ext()去掉文件名的.csv后缀,让生成的列名更干净。
内容的提问来源于stack exchange,提问作者Lukas015
相关产品推荐
相关产品推荐

