You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用pivot_longer拆分带时间后缀列生成指定长格式数据?

问题:使用pivot_longer将宽格式数据转换为长格式的正确正则写法

需求说明

现有宽格式数据框,部分列名以_0m、_6m、_12m为后缀表示数据采集月份,需要用pivot_longer转换为长格式,生成Month列(取值为0m、6m、12m),同时保留test1和score列存储对应人员、月份的结果。

宽格式数据

wide = data.frame(id = c(1:5),
                 agree = c("y","n","n","y","y"),
                 test1_0m = c(2,3,4,3,5),
                 test1_6m = c(3,5,2,6,7),
                 test1_12m = c(6,7,8,4,5),
                 score_0m = c(55,44,33,22,11),
                 score_6m = c(77,66,55,44,33),
                 score_12m = c(99,88,77,66,55))

错误尝试代码

wide%>%
  pivot_longer(cols = contains("_"), 
               names_to = c("Month", ".value"), 
               names_pattern = "(.*\\_)(.*)",
               values_drop_na = TRUE )

期望输出

long
   id agree Month test1 score
1   1     y    0m     2    55
2   2     n    0m     3    44
3   3     n    0m     4    33
4   4     y    0m     3    22
5   5     y    0m     5    11
6   1     y    6m     3    77
7   2     n    6m     5    66
8   3     n    6m     2    55
9   4     y    6m     6    44
10  5     y    6m     7    33
11  1     y   12m     6    99
12  2     n   12m     7    88
13  3     n   12m     8    77
14  4     y   12m     4    66
15  5     y   12m     5    55

正确解法

错误核心在于两点:

  1. names_to顺序错误:.value对应要保留的列名(test1、score),需放在Month之前;
  2. 正则分组逻辑错误:原正则(.*\\_)(.*)会把包含下划线的内容归为第一组,而我们需要将下划线前的字段名(如test1)作为第一组对应.value,下划线后的月份(如0m)作为第二组对应Month。

正确代码如下:

library(tidyr)

wide %>%
  pivot_longer(
    cols = contains("_"),
    names_to = c(".value", "Month"),
    names_pattern = "(.*)_(.*)",
    values_drop_na = TRUE
  )

运行后即可得到期望的长格式数据。

内容的提问来源于stack exchange,提问作者Mark Davies

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 00:35:22