R – 混淆矩阵中缺失因子的条件替换

我正在为一个大型样本点数据集创建混淆矩阵,并需要使用R包caret中的confusionMatrix函数对它们进行循环(我使用的是输出中的准确性指标,即我不能仅使用table)。每个样本点集应该有三个类/因子,即我应该有3×3的表格,然而一些参考和预测数据包含少于两个类,或者类别不重叠,例如:

 Class  A  B             Class  C   A    8  2               A    3   B    1  0   C    1  7* 列 = 参考数据,行 = 预测数据

我需要相同数量的类/因子来运行confusionMatrix,所以我想做的是有条件地用零替换缺失的因子,像这样:

 Class  A  B  C          Class  A  B  C   A    8  2  0            A    0  0  3   B    1  0  0            B    0  0  0   C    1  7  0            C    0  0  0

我使用的预测/参考数据是数值列表的值,所以我不会在这里重现它们;对于我上面提供的示例,您可以将其视为仅是一个向量,如下所示:

predicted.data[1] = A A A A A A A A A A B C C C C C C C Creference.data[1] = A A A A A A A A A A B B B B B B B B Bpredicted.data[2] = A A Areference.data[2] = C C C 

我尝试创建某种条件if语句,类似于:

   tab <- table(predicted.data, reference.data)   if(nrow(tab) != ncol(tab){   classes <- c("A","B","C")   missing <- setdiff(classes,names(tab))   ...   ...   }# 显然会将实际数据放入循环/索引中

但我似乎无法按我想要的方式使其工作。有什么想法吗?

编辑:我使用的实际数据示例(通过栅格/形状文件)和错误消息;数据长度相同,但没有参考数据被分类为’2’:

> mask.vals[[4]]  [1] 0 4 0 0 0 2 4 0 4 0 4 0 0 0 0 0 4 0 4 2 0 0 0 0 0 0 0 4 0 0 0 0 0 0 4 0 0 0 0 0 0 0 0 2 2 0 2 0 4 0 0 4 2 0 0 4 0 0 0 0 0 0 0 2 0 2 0 2 4 0 4 [72] 4 0 0 0 0 4 4 0 0 0 0 0 0 0 4 0 0 0 0 4 4 4 4 0 4 4 4 4 4 0 4 4 4 0 4 0 0 4 4 4 4 4 4> ref.data[[4]]@data$CLASS_ID  [1] 0 4 4 4 4 4 4 4 4 4 4 4 4 4 0 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 [72] 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4 4> confusionMatrix(data = mask.vals[[4]], reference = ref.data[[4]]@data$CLASS_ID)Error in confusionMatrix.default(data = mask.vals[[4]], reference = ref.data[[4]]@data$CLASS_ID) :   the data cannot have more levels than the reference

即需要从这个:

> table(mask.vals[[4]], ref.data[[4]]@data$CLASS_ID)        0  4             0    2  67                 2    0  9   4    0  36

变为这个:

        0  2  4             0    2  0  67                 2    0  0  9   4    0  0  36

即使我为数据定义了三个级别(例如levels(ref.data[[4]]@data$CLASS_ID) <- c("0","2","4")factor(ref.data[[4]]@data$CLASS_ID, levels = c("0","2","4")),这个错误仍然存在…


回答:

caret包中的confusionMatrix函数会返回一个n x n的表格,无论参考和/或预测向量中是否缺少某些级别。我想知道你是如何设法得到一个混淆矩阵,其中一些参考数据列缺失的。例如,使用内置的iris数据框架:

library(caret)set.seed(2)dat = data.frame(ref=iris$Species, pred=sample(iris$Species))# 从参考数据中移除两个级别dat1 = dat[dat$ref=="setosa", ]# 获取混淆矩阵cm1 = confusionMatrix(dat1$pred, dat1$ref)cm1$table
            ReferencePrediction   setosa versicolor virginica  setosa         15          0         0  versicolor     15          0         0  virginica      20          0         0
# 参考和预测之间没有重叠dat2 = dat[dat$ref=="setosa" & dat$pred=="versicolor", ]# 获取混淆矩阵cm2 = confusionMatrix(dat2$pred, dat2$ref)cm2$table
            ReferencePrediction   setosa versicolor virginica  setosa          0          0         0  versicolor     15          0         0  virginica       0          0         0

在上面的示例中,refpred列都被编码为具有Species原始三个级别的因子。我们可以重新编码它们以删除空级别:

dat2$ref = droplevels(dat2$ref)dat2$pred = droplevels(dat2$pred)

您可以看到每个列中只有一个因子级别存在:

lapply(dat2, levels)    
$ref [1] "setosa"$pred [1] "versicolor"

但如果您运行confusionMatrix,现在会抛出错误,因为两个向量的级别之间没有重叠:

cm3 = confusionMatrix(dat2$pred, dat2$ref)

Error in confusionMatrix.default(dat2$pred, dat2$ref) : The data must contain some levels that overlap the reference.

更新: 如果您在参考向量和预测向量中设置相同的因子级别,confusionMatrix将正常工作。您已经更新了问题,但它仍然不可重现,因此很难确定您的工作流程中哪里出了问题。现在,这里有一个与您在问题中显示的类似且在设置公共因子级别后按预期工作的示例。

library(caret)set.seed(2)mask.vals = sample(c(0,2,4), 100, replace=TRUE)ref.data = rep(4,100)cm = confusionMatrix(mask.vals, ref.data)
Error in confusionMatrix.default(mask.vals, ref.data) :   the data cannot have more levels than the reference
mask.vals = factor(mask.vals, levels=c(0,2,4))ref.data = factor(ref.data, levels=c(0,2,4))cm = confusionMatrix(mask.vals, ref.data) cm$table
          ReferencePrediction  0  2  4         0  0  0 35         2  0  0 31         4  0  0 34

Related Posts

使用LSTM在Python中预测未来值

这段代码可以预测指定股票的当前日期之前的值,但不能预测…

如何在gensim的word2vec模型中查找双词组的相似性

我有一个word2vec模型,假设我使用的是googl…

dask_xgboost.predict 可以工作但无法显示 – 数据必须是一维的

我试图使用 XGBoost 创建模型。 看起来我成功地…

ML Tuning – Cross Validation in Spark

我在https://spark.apache.org/…

如何在React JS中使用fetch从REST API获取预测

我正在开发一个应用程序,其中Flask REST AP…

如何分析ML.NET中多类分类预测得分数组?

我在ML.NET中创建了一个多类分类项目。该项目可以对…

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注