如何计算平均生存时间

13

我正在使用survival库。在计算生存函数的Kaplan-Meier估计器之后:

km = survfit(Surv(time, flag) ~ 1)

我知道如何计算百分位数:

quantile(km, probs = c(0.05,0.25,0.5,0.75,0.95))

但是,我该如何计算平均生存时间?

3个回答

25

计算平均生存时间

平均生存时间一般取决于最大生存时间的取值。您可以使用print(km, print.rmean=TRUE)获取受限平均生存时间。默认情况下,它假定最长的生存时间等于数据中最长的生存时间。您可以通过添加rmean参数(例如:print(km, print.rmean=TRUE, rmean=250))将其设置为不同的值。

提取平均生存时间的值并存储在一个对象中

针对您的评论:我最初认为可以通过查看print(km, print.rmean=TRUE)返回的对象来提取平均生存时间,但事实证明print.survfit没有返回列表对象,而只是向控制台返回文本。

相反,我查看了print.survfit的代码(您可以在控制台中键入getAnywhere(print.survfit)查看代码),以查看平均生存时间是如何计算的。结果发现,一个名为survmean的函数处理了这个问题,但它不是一个导出函数,这意味着当您尝试像运行“正常”函数一样运行它时,R将无法识别该函数。因此,要访问该函数,您需要运行下面的代码(其中您需要明确设置rmean):

survival:::survmean(km, rmean=60) 
您会发现该函数返回一个列表,其中第一个元素是一个包括多个命名值的矩阵,包括平均值和平均标准误差。因此,如果想要提取例如平均生存时间,您可以执行以下操作:

您将看到该函数返回一个列表,其中第一个元素是一个矩阵,其中包含多个命名值,包括平均值和平均标准误差。所以,如果要提取例如平均生存时间,您可以执行以下操作:

survival:::survmean(km, rmean=60)[[1]]["*rmean"]

如何计算平均生存时间的详细信息

print.survfit的帮助文档提供了有关选项以及如何计算受限平均值的详细信息:

?print.survfit 
均值及其方差是基于截尾估计的。也就是说,如果最后一次观测不是死亡事件,则生存曲线估计不会趋近于零,均值将无法定义。有四种可能的方法来解决这个问题,这些方法由rmean选项选择。第一种方法是将上限设置为常数,例如rmean=365。在这种情况下,报告的平均数将是每组前365天预期经历的天数。如果关注的是一个固定的时间段,这是有用的。其他选项包括“none”(没有估计)、“common”和“individual”。“common”选项使用对象中所有曲线的最长时间作为auc计算的公共上限。对于“individual”选项,平均值被计算为每条曲线在从0到该曲线的最大观测时间范围内的面积。由于终点是随机的,不同曲线的值不可比较,并且打印的标准误差低估了随机变化。此选项主要是为向后兼容提供的,因为在早期版本的代码中,该估计值是默认(唯一)的估计值。请注意,SAS(截至9.3版)使用每个个体曲线的最后事件时间之前的积分;我们认为这是最糟糕的选择,因此不提供该计算的选项。

好的,谢谢!有没有一种直接将受限均值存储到变量中的方法,还是我必须从“print”的输出中复制它? - isekaijin
2
非常感谢!我想再次给你点赞,但我不能。 :-| - isekaijin
1
也许由于问题的提出,survival包已经更新以实现此功能,但是今天不需要使用“隐藏”的survival:::survmean(km, rmean=60)。只需使用summary(km)$table[,5:6]即可,它会给出RMST及其SE。可以使用正态分布的适当分位数来计算CI。 - Bastian
@Bastian 我想你的意思是 summary(km)$table[5:6],对于整个生存曲线的RMST工作正常。但是,如果我们想提取特定时间点的RMST,我们仍然没有其他解决方案,只能使用 survival:::survmean(km, rmean = 60) - Seanosapien
我想提取相同的值,但是我得到了“错误:从'namespace:survival'中未导出对象'survmean'”,尽管当我运行getAnywhere(print.survfit)时,我可以看到survmean。任何帮助都将不胜感激。 - gladys_c_hugh
回答自己的问题:可以使用 summary(km, rmean = 60)$table[,"rmean"] - 我猜这就是 @Bastian 的意思,只是在总结调用中缺少了 rmean = 60 参数。 - gladys_c_hugh

2
使用尾数公式(由于我们的变量为非负),您可以将平均数计算为从0到无穷大的积分 1-CDF,该积分等于生存函数的积分。
如果我们用非参数 KM 估计替换参数生存曲线,则生存曲线仅延伸到数据集中的最后时间点。从那以后,它“假定”线继续直线。因此,我们只能“有限制地”使用尾数公式,直到某个截止点,我们可以定义该点(默认为我们数据集中的最后时间点)。
您可以使用打印功能或手动计算。
print(km, print.rmean=TRUE) # print function
sum(diff(c(0,km$time))*c(1,km$surv[1:(length(km$surv)-1)])) # manually

我在时间向量的开头添加了0,同时在生存向量的开头添加了1,因为它们并没有包含在内。我只取生存向量到最后一个点,因为那是最后一块。这基本上计算了你的数据中生存曲线在最后一个时间点之前的面积。
如果您在最后一个点之后设置了手动截断点,则会简单地添加该区域;例如,在这里:
print(km, print.rmean=TRUE, rmean=4) # gives out 1.247
print(km, print.rmean=TRUE, rmean=4+2) # gives out 1.560
1.247+2*min(km$surv) # gives out 1.560

如果截止值低于最后一个值,它只会计算KM曲线到该点的面积。

谢谢你的回答!我知道这个工作原理的理论,但当时我不知道如何在R中具体实现,我真的想确保我没有错过survival库中可以为我计算的选项。 - isekaijin
2
欢迎。我想特别为手动计算添加这个内容。 - Maverick Meerkat

2

不需要使用"hidden" survival:::survmean(km, rmean=60)

只需使用summary(km)$table[,5:6],它会给出RMST及其SE。可以使用正态分布的适当分位数来计算CI。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接