【问题标题】:Plot A Confusion Matrix with Color and Frequency in R在 R 中绘制具有颜色和频率的混淆矩阵
【发布时间】:2019-05-23 21:24:41
【问题描述】:

我想绘制一个混淆矩阵,但我不想只使用热图,因为我认为它们的数值分辨率很差。相反,我还想在正方形中间绘制频率。例如,我喜欢这样的输出:

library(mlearning);
data("Glass", package = "mlbench")
Glass$Type <- as.factor(paste("Glass", Glass$Type))

summary(glassLvq <- mlLvq(Type ~ ., data = Glass));
(glassConf <- confusion(predict(glassLvq, Glass, type = "class"), Glass$Type))

plot(glassConf) # Image by default

但是,1.) 我不明白“01、02 等”是指沿每个轴。我们怎样才能摆脱它? 2.)我希望“预测”作为“y”维度的标签,“实际”作为“x”维度的标签 3.) 我想用频率/概率替换绝对计数。

或者,是否有其他软件包可以做到这一点?

本质上,我希望在 R 中这样:

http://www.mathworks.com/help/releases/R2013b/nnet/gs/gettingstarted_nprtool_07.gif

或者:

http://c431376.r76.cf2.rackcdn.com/8805/fnhum-05-00189-HTML/image_m/fnhum-05-00189-g009.jpg

【问题讨论】:

    标签: r plot confusion-matrix


    【解决方案1】:

    mlearning 包在绘制混淆矩阵方面似乎相当不灵活。

    从您的 glassConf 对象开始,您可能想要执行以下操作:

    prior(glassConf) <- 100 
    # The above rescales the confusion matrix such that columns sum to 100.
    opar <- par(mar=c(5.1, 6.1, 2, 2))
    x <- x.orig <- unclass(glassConf)
    x <- log(x + 0.5) * 2.33
    x[x < 0] <- NA
    x[x > 10] <- 10
    diag(x) <- -diag(x)
    image(1:ncol(x), 1:ncol(x),
          -(x[, nrow(x):1]), xlab='Actual', ylab='',
          col=colorRampPalette(c(hsv(h = 0, s = 0.9, v = 0.9, alpha = 1), 
                                 hsv(h = 0, s = 0, v = 0.9, alpha = 1), 
                                 hsv(h = 2/6, s = 0.9, v = 0.9, alpha = 1)))(41), 
          xaxt='n', yaxt='n', zlim=c(-10, 10))
    axis(1, at=1:ncol(x), labels=colnames(x), cex.axis=0.8)
    axis(2, at=ncol(x):1, labels=colnames(x), las=1, cex.axis=0.8)
    title(ylab='Predicted', line=4.5)
    abline(h = 0:ncol(x) + 0.5, col = 'gray')
    abline(v = 0:ncol(x) + 0.5, col = 'gray')
    text(1:6, rep(6:1, each=6), 
         labels = sub('^0$', '', round(c(x.orig), 0)))
    box(lwd=2)
    par(opar) # reset par
    

    上面的代码使用了plot.confusion调用的confusionImage函数的一些片段。

    【讨论】:

      【解决方案2】:

      这是我从 jbaums 优秀答案开发的用于绘制混淆矩阵的函数。
      它很相似,但看起来更好一些(IMO),并且不会转置您提供的混淆矩阵,这可能会有所帮助。

      ### Function for plotting confusion matrices
      confMatPlot = function(confMat, titleMy, shouldPlot = T) {
        #' Function for plotting confusion matrice
        #' 
        #' @param confMat: confusion matrix with counts, ie integers. 
        #' Fractions won't work
        #' @param titleMy: String containing plot title
        #' @return Nothing: It only plots
      
        ## Prepare data
        x.orig = confMat; rm(confMat)  # Lazy conversion to function internal variable name
        n = nrow(x.orig)  # conf mat is square by definition, so nrow(x) == ncol(x)
        opar <- par(mar = c(5.1, 8, 3, 2))
        x <- x.orig
        x <- log(x + 0.5)  # x<1 -> x<0 ,  x>=1 -> x>0
        x[x < 0] <- NA
        diag(x) <- -diag(x)  # change sign to give diagonal different color
        ## Plot confusion matrix
        image(1:n, 1:n,  # grid of coloured boxes
              # matrix giving color values for the boxes
              # t() and [,ncol(x):1] since image puts [1,1] in bottom left by default
              -t(x)[, n:1],  
              # ylab added later to avoid overlap with tick labels
              xlab = 'Actual', ylab = '',
              col = colorRampPalette(c("darkorange3", "white", "steelblue"), 
                                     bias = 1.65)(100),
              xaxt = 'n', yaxt = 'n'
              )
        # Plot counts
        text(rep(1:n, each = n), rep(n:1, times = n), 
             labels = sub('^0$', '', round(c(x.orig), 0)))
        # Axis ticks but no lables
        axis(1, at = 1:n, labels = rep("", n), cex.axis = 0.8)
        axis(2, at = n:1, labels = rep("", n), cex.axis = 0.8)
        # Tilted axis lables
        text(cex = 0.8, x = (1:n), y = -0.1, colnames(x), xpd = T, srt = 30, adj = 1)
        text(cex = 0.8, y = (n:1), x = +0.1, colnames(x), xpd = T, srt = 30, adj = 1)
        title(main = titleMy)
        title(ylab = 'Predicted', line = 6)
        # Grid and box
        abline(h = 0:n + 0.5, col = 'gray')
        abline(v = 0:n + 0.5, col = 'gray')
        box(lwd = 1, col = 'gray')
        par(opar)
      }
      

      输出示例:

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2016-01-31
        • 2016-10-20
        • 1970-01-01
        • 2022-01-02
        • 2016-09-27
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多