使用tidyr的pivot_longer时names_sep按点分割失效问题排查
问题:pivot_longer使用点(.)作为names_sep无法生效的原因及解决办法
在使用tidyr包的pivot_longer()函数时,尝试通过names_sep参数将列名拆分为两部分,但用点(.)作为分隔符时无法生效;换成下划线(_)(同时修改对应列名)或用数字位置(如4)作为分隔依据时功能正常。但官方文档里用点做分隔符是可行的,问题出在哪里?
无法生效的代码示例
test_df <- tibble( Zeit_Mod = 1:4, DC1.U = c(1, 1,0, 0), DC1.I = c(0, 1, 1, 1), DC1.P = rnorm(4), DC2.U = rnorm(4), DC2.I = rep(3, 4), DC2.P = rep(-2, 4), ) test_df_pivoted <- test_df %>% pivot_longer(cols = contains("DC"), names_to = c("String", "Variable"), values_to = "Measurement", names_sep = "." )
可正常运行的代码示例
test_df <- tibble( Zeit_Mod = 1:4, DC1_U = c(1, 1,0, 0), DC1_I = c(0, 1, 1, 1), DC1_P = rnorm(4), DC2_U = rnorm(4), DC2_I = rep(3, 4), DC2_P = rep(-2, 4), ) test_df_pivoted <- test_df %>% pivot_longer(cols = contains("DC"), names_to = c("String", "Variable"), values_to = "Measurement", names_sep = "_" )
原因及解决办法
问题核心:names_sep参数默认将传入的字符串解析为正则表达式,而点(.)在正则里是特殊字符,代表匹配任意单个字符,而非字面意义上的点。因此直接用"."会导致拆分逻辑混乱,无法得到预期结果。
有两种可行的解决方式:
- 方式一:转义点字符:用双反斜杠
\\.表示字面意义的点,让正则引擎识别为普通字符 - 方式二:使用
fixed()函数:通过fixed(".")告诉函数将点当作普通文本处理,不解析为正则
修改后的可运行代码
test_df <- tibble( Zeit_Mod = 1:4, DC1.U = c(1, 1,0, 0), DC1.I = c(0, 1, 1, 1), DC1.P = rnorm(4), DC2.U = rnorm(4), DC2.I = rep(3, 4), DC2.P = rep(-2, 4), ) # 方式一:转义点 test_df_pivoted1 <- test_df %>% pivot_longer(cols = contains("DC"), names_to = c("String", "Variable"), values_to = "Measurement", names_sep = "\\." ) # 方式二:使用fixed() test_df_pivoted2 <- test_df %>% pivot_longer(cols = contains("DC"), names_to = c("String", "Variable"), values_to = "Measurement", names_sep = fixed(".") )
内容的提问来源于stack exchange,提问作者Johannes
相关产品推荐
相关产品推荐

