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

R语言使用pivot_longer()转换多列生存数据为长格式的问题

R语言pivot_longer宽转长生存分析数据实现方案

需求说明

  • 原始宽表字段:Time(时间)、Cohort1/Cohort2(两个队列的生存概率)、C1Lower95/C1Upper95(队列1的95%CI上下限)、C2Lower95/C2Upper95(队列2的95%CI上下限)
  • 目标长表字段:Time、Cohort(队列标识)、Survival(生存概率)、Lower95(95%CI下限)、Upper95(95%CI上限),用于ggplot2绘制生存曲线

原有写法错误点

  • 第一次尝试错误:未配置列名拆分规则,直接将所有非Time列转为单列值,无法自动区分生存概率、CI上下限三类不同指标,输出结构错位。
  • 第二次尝试错误:一是read_excel函数多写了一个skip参数存在语法错误;二是重命名列时规则不统一,没有将「指标类型」「队列标识」设置为可拆分的两个维度,导致.value参数无法正确匹配值对应的字段。

正确实现代码

方法1:正则匹配法(无需修改初始列重命名逻辑)

利用列名固定规律通过正则提取信息,不需要调整第一步写的列重命名规则,直接运行即可:

library(tidyr)
library(dplyr)
library(ggplot2)
library(readxl)

# 数据读取与初始重命名(修正原代码语法错误即可)
km_curve <- read_excel("/Users/xxx/Desktop/dataset for reshape test.xlsx", skip = 1) %>% 
  transmute(
    Time = `Time (Days)`, 
    Cohort1 = `Cohort 1: Survival Probability`,
    Cohort2 = `Cohort 2: Survival Probability`, 
    C1Lower95 = `Cohort 1: Survival Probability 95 % CI Lower`, 
    C1Upper95 = `Cohort 1: Survival Probability 95 % CI Upper`, 
    C2Lower95 = `Cohort 2: Survival Probability 95 % CI Lower`, 
    C2Upper95 = `Cohort 2: Survival Probability 95 % CI Upper`
  ) 

# 核心宽转长逻辑
km_long <- km_curve %>%
  pivot_longer(
    cols = -Time,
    names_to = c("Cohort", ".value"),
    # 正则匹配列名规则:提取队列编号、指标后缀两个部分
    names_pattern = "^C(?:ohort)?(\\d)(.*)$",
    # 对提取到的内容做标准化映射
    names_transform = list(
      Cohort = ~paste0("Cohort", .x),
      .value = ~recode(.,
                       "" = "Survival",
                       "Lower95" = "Lower95",
                       "Upper95" = "Upper95")
    )
  )

*代码逻辑说明:正则^C(?:ohort)?(\\d)(.*)$会匹配所有以C开头的指标列,不管C后面是ohort加数字,还是直接跟数字加CI后缀,自动捕获数字作为队列编号,剩余后缀作为指标类型,无后缀的列自动识别为生存概率值。

方法2:规范命名分隔符法(逻辑更适合新手理解)

重命名列时严格遵循指标名_队列名的统一规则,通过下划线直接拆分,不需要写正则:

km_curve <- read_excel("/Users/xxx/Desktop/dataset for reshape test.xlsx", skip = 1) %>% 
  transmute(
    Time = `Time (Days)`, 
    # 所有指标列统一命名为「指标类型_队列编号」格式
    Survival_Cohort1 = `Cohort 1: Survival Probability`,
    Survival_Cohort2 = `Cohort 2: Survival Probability`, 
    Lower95_Cohort1 = `Cohort 1: Survival Probability 95 % CI Lower`, 
    Upper95_Cohort1 = `Cohort 1: Survival Probability 95 % CI Upper`, 
    Lower95_Cohort2 = `Cohort 2: Survival Probability 95 % CI Lower`, 
    Upper95_Cohort2 = `Cohort 2: Survival Probability 95 % CI Upper`
  ) 

km_long <- km_curve %>%
  pivot_longer(
    cols = -Time,
    names_to = c(".value", "Cohort"),
    names_sep = "_"
  )

后续绘图参考

转换完成的长表可直接用于绘制带置信区间的生存曲线:

ggplot(km_long, aes(x = Time, y = Survival, color = Cohort, fill = Cohort)) +
  geom_line(linewidth = 1) +
  geom_ribbon(aes(ymin = Lower95, ymax = Upper95), alpha = 0.2, color = NA) +
  scale_x_continuous(name = "随访时间(天)") +
  scale_y_continuous(name = "生存概率", limits = c(0,1)) +
  theme_bw()

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.28 15:48:17