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

如何在R中基于日期指标重塑数据并关联对应类型信息?

R语言数据重塑:宽格式转长格式并匹配Type信息

原始数据

df <- data.frame(
  ID = c(1, 2),
  Day1 = c(1, 1),
  Type1 = c('A', 'B'),
  EX1 = c(1, 3),
  EX2 = c(4, 5),
  Time1 = c(13, 15),
  Time2 = c(9, 10),
  Day2 = c(2, 2),
  Type2 = c('B', 'D'),
  EX3 = c(7, 6),
  EX4 = c(8, 9),
  Time3 = c(10, 4),
  Time4 = c(6, 12)
)

需求说明

将上述宽格式数据转换为长格式,每行对应一个ID的单次记录,需满足:

  • 每个记录匹配对应Day的Type(Day1对应Type1,Day2对应Type2)
  • 提取EX字段的数值作为Exer,保留其序号(如EX1→1,EX2→2)
  • 提取Time字段的数值作为Score,保留其序号作为Time(如Time1→1,Time2→2)
  • 确保EX和Time的序号一一对应

解决方案

方法1:分Day处理(适合字段数量明确的场景)

使用tidyverse工具包,拆分Day1和Day2的字段分别处理后合并:

library(tidyverse)

# 处理Day1相关数据
df_day1 <- df %>%
  select(ID, Type = Type1, starts_with(c("EX1", "EX2", "Time1", "Time2"))) %>%
  pivot_longer(
    cols = starts_with(c("EX", "Time")),
    names_to = c(".value", "Exer"),
    names_pattern = "(EX|Time)(\\d+)"
  ) %>%
  rename(Score = Time) %>%
  mutate(Exer = as.integer(Exer))

# 处理Day2相关数据
df_day2 <- df %>%
  select(ID, Type = Type2, starts_with(c("EX3", "EX4", "Time3", "Time4"))) %>%
  pivot_longer(
    cols = starts_with(c("EX", "Time")),
    names_to = c(".value", "Exer"),
    names_pattern = "(EX|Time)(\\d+)"
  ) %>%
  rename(Score = Time) %>%
  mutate(Exer = as.integer(Exer))

# 合并并排序得到结果
result <- bind_rows(df_day1, df_day2) %>% arrange(ID, Exer)

print(result)

输出结果:

ID Type Exer Score
1  1    A    1    13
2  1    A    2     9
3  1    B    3    10
4  1    B    4     6
5  2    B    1    15
6  2    B    2    10
7  2    D    3     4
8  2    D    4    12

方法2:通用处理(适合大量EX/Time字段的场景)

如果存在大量EX和Time字段,可通过字段序号自动匹配所属Day,无需手动指定字段:

library(tidyverse)

result_general <- df %>%
  # 将非ID/Type的字段转长,拆分类型和序号
  pivot_longer(
    cols = -c(ID, Type1, Type2),
    names_to = c("Category", "Num"),
    names_pattern = "(Day|EX|Time)(\\d+)"
  ) %>%
  # 转回宽格式,按序号聚合Day/EX/Time值
  pivot_wider(names_from = Category, values_from = value) %>%
  # 根据Day值匹配对应Type
  mutate(Type = case_when(Day == 1 ~ Type1, Day == 2 ~ Type2)) %>%
  # 过滤有效记录(去掉仅含Day的行)
  drop_na(EX, Time) %>%
  # 整理列名和类型,排序
  select(ID, Type, Exer = Num, Time = Num, Score = Time) %>%
  mutate(across(c(Exer, Time), as.integer)) %>%
  arrange(ID, Exer)

print(result_general)

该方法通过字段序号关联Day、EX和Time,自动匹配Type,扩展性更强,适用于字段数量较多的场景。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.26 03:23:19