如何在需要两个输入语句的函数循环中输入 varying 语句?

How does one enter the varying statement in a loop of a function requiring two input statements?

我是 R 的新手并且已经搜索过,但没有找到 query/answer 可以满足我正在尝试为其编写脚本的需求。我正在尝试循环 pROC 包中的 roc() 函数来计算多个 ROC 曲线的几个参数。我的数据看起来像这样,只是有更多的行和列(我的 df 在后面的代码中称为 ROCTest5):

Outcome A B C D E BiOutcome <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> Good 21151. 4966. 1943. 646. 277. 1. Good 46278. 9408. 2810. 906. 856. 1. Poor 4717. 2153. 758. 215. 148. 0. Poor 14488. 4661. 1167. 530. 299. 0.

如果我 运行 每个 ROC 手动分析,这不是较大数据集的选项,我会使用以下代码:

ROCvirus = roc(ROCTest5$Outcome,
            ROCTest5$A,
            plot=TRUE, grid=TRUE,
            print.auc=TRUE, show.thres=TRUE)

aucA = auc(ROCvirus, as.vector=T)

ROCViCoorBest = coords(ROCvirus,"best",input=c("threshold", "specificity", "sensitivity", "accuracy",
                                       "tn", "tp", "fn", "fp", "npv", "ppv"), as.list=T)

我一直试图用来创建循环的代码如下所示:

library(pROC)

rocData = NULL
for(i in ROCTest5[A:E]){
 rocValue = roc(ROCTest5$Outcome,
             ROCTest5[[i in A:E]], #issue is here!
             plot=FALSE, auc=TRUE)
rocCoordi = coords(rocValue,"best",input=c("threshold", "specificity", "sensitivity", "accuracy",
                                         "tn", "tp", "fn", "fp", "npv", "ppv"))
rocValue = rbind(rocValue,rocCoordi)
rocData = cbind(rocData,rocValue)
}

此代码不起作用,因为我没有正确输入第二个输入参数的语句,该参数将随着循环的每次迭代而更改。我尝试了几种不同的方法来做到这一点,例如使用第二个 "for" 语句,但无法使脚本工作。我还尝试使用 "apply" 函数对此进行脚本编写,但 运行 进入了相同的一般问题。 如何在需要两个输入语句的函数循环中输入 varying 语句? 如果您对代码有更正,或者就此而言,采用完全不同的方法来实现我的目标,我会洗耳恭听。提前致谢!

解决此问题的更好方法是使用 apply 语句。在 base R 中,您可以通过调用

list_of_results <- lapply(LETTERS[1:5], function(x) {
  ROCvirus = roc(ROCTest5$Outcome,
        ROCTest5[[x]],
        plot=TRUE, grid=TRUE,
        print.auc=TRUE, show.thres=TRUE)
  auc_result <- auc(ROCvirus, as.vector=T)
  ROCViCoorBest = coords(ROCvirus,"best",ret=c("threshold", "specificity", "sensitivity", "accuracy",
                                       "tn", "tp", "fn", "fp", "npv", "ppv"), as.list=T)
  list(ROCvirus = ROCvirus, auc = auc_result, ROCViCoorBest = ROCViCoorBest)
})

应该 return 一个长度为 5 的列表,第一个条目是 A 的结果,...到第 5 个条目是 E 的结果。

函数的内容直接取自您添加的第一段代码。要使用列表,您可以提取元素。查看 coords 的帮助文件,看起来 return 是一个向量,所以我们可以这样做:

rocValue <- sapply(list_of_results, function(x) { x$ROCViCoorBest})

这将是一个矩阵,可能是您想要的矩阵的转置。使用 t 转置它。

下面的脚本有效,并生成一个有序的 df:

list_of_results = lapply(LETTERS[1:5], function(x) {
ROCvirus = roc(ROCTest5$Outcome,
             ROCTest5[[x]])
auc_result = auc(ROCvirus)
ROCViCoorBest = coords(ROCvirus,"best",
                     ret=c("threshold", "specificity",
                           "sensitivity", "accuracy"),
                     best.method="closest.topleft")
ROCDat = c(as.numeric(auc_result), as.numeric(ROCViCoorBest))

list(ROCDat = ROCDat)
})  
Lab = c("AUC","threshold", "specificity",
      "sensitivity", "accuracy")
OutputData=as.data.frame(list_of_results)
OutputData=cbind(Lab,OutputData)

OutputData

Lab ROCDat ROCDat.1 ROCDat.2 ROCDat.3 ROCDat.4 AUC 7.592593e-01 0.8518519 0.9074074 0.9074074 0.7962963 threshold 1.475129e+04 5395.7471701 2361.0867577 1072.7211367 361.2662753 specificity 6.666667e-01 0.7777778 0.7777778 0.7777778 0.7777778 sensitivity 6.666667e-01 0.8333333 0.8333333 1.0000000 0.8333333 accuracy 6.666667e-01 0.8000000 0.8000000 0.8666667 0.8000000