代码之家  ›  专栏  ›  技术社区  ›  nalzok granmirupa

优化roc绘图的基本原理是什么?

  •  0
  • nalzok granmirupa  · 技术社区  · 5 年前

    我在读书 this Rnews document from June 2004 ,以及文章 程序员利基 从第33页提出了一种绘制接收机工作特性曲线的方法,并对其进行了优化。

    第一个代码片段很简单,并且与定义一致

    drawROC.A <- function(T, D) {
        cutpoints <- c(-Inf, sort(unique(T)), Inf)
        sens <- sapply(cutpoints,
                       function(c) sum(D[T>c])/sum(D))
        spec <- sapply(cutpoints,
                       function(c) sum((1-D)[T<=c]/sum(1-D)))
    
        plot(1-spec, sens, type = "l")
    }
    

    然后作者说(我做了些小修改)

    有一个相对简单的函数优化 大大提高了速度,尽管代价是 T 作为一个数字,而不仅仅是一个对象 > <= 是 定义

    drawROC.B <- function(T, D){
      DD <- table(-T, D)
      sens <- cumsum(DD[ ,2]) / sum(DD[ ,2])
      mspec <- cumsum(DD[ ,1]) / sum(DD[ ,1])
    
      plot(mspec, sens, type="l")
    }
    

    我花了相当长的时间阅读优化版本,但却停留在第一行:它看起来像是负号 - 前面的 t 用于按相反顺序执行累积和,但为什么?

    困惑的是,我把两个函数产生的roc绘制在一起,检查结果是否相同。

    enter image description here

    左图由 drawROC.A 而正确的是 drawROC.B . 乍一看,它们并不相同,但如果仔细观察,y轴的范围是不同的,所以它们实际上是同一个图。

    编辑:

    现在我明白了 抽签B 是正确的(见下面我的回答),但我仍然不知道实质性的性能提升来自哪里…

    0 回复  |  直到 5 年前
        1
  •  0
  •   nalzok granmirupa    5 年前

    我想我已经弄明白了。这个 DD <- table(-T, D) 是以相反的顺序执行累积和,这是因为我们正在计算pr(t>c),而表的累积和是计算t中小于或等于当前元素的元素数。

    换句话说,这也会起作用,因为pr(t>c)=1-pr(t<=c)。

    drawROC.B <- function(T, D){
      DD <- table(T, D)
      sens <- 1 - cumsum(DD[ ,2])/sum(DD[ ,2])
      mspec <- 1 - cumsum(DD[ ,1])/sum(DD[ ,1])
    
      plot(mspec, sens, type="l")
    }
    

    顺便说一下,你可以用这个来把两点(0, 0)和(1, 1)加到结果中。 drawROC.B

    drawROC.C <- function(T, D){
      DD <- table(-T, D)
      sens <- c(0, cumsum(DD[ ,2])/sum(DD[ ,2]), 1)
      mspec <- c(0, cumsum(DD[ ,1])/sum(DD[ ,1]), 1)
    
      plot(mspec, sens, type="l")
    }
    

    至于性能增益,请注意 drawROC.A 需要执行(渐近) unique(T) * length(T) 比较,然而 拖曳物 只采取 length(T) 构建表的操作和所有后续操作都同样昂贵。