Почему мои графики ROC и значение AUC выглядят хорошо, когда моя матрица путаницы из случайных лесов показывает, что модель не годится для прогнозирования заболеваний?

Я использую пакет randomForest в R, чтобы создать модель для классификации случаев на болезни (1) или свободные от болезней (0):

classify_BV_100t <- randomForest(bv.disease~., data=RF_input_BV_clean, ntree = 100, localImp = TRUE)

print(classify_BV_100t)

Call:
 randomForest(formula = bv.disease ~ ., data = RF_input_BV_clean,      ntree = 100, localImp = TRUE) 
           Type of random forest: classification
                 Number of trees: 100
No. of variables tried at each split: 53

    OOB estimate of  error rate: 8.04%
Confusion matrix:
    0  1 class.error
0 510  7  0.01353965
1  39 16  0.70909091

Моя матрица путаницы показывает, что модель хороша для классификации 0 (нет болезни), но очень плохо для классификации 1 (болезни).

Но когда я строю графики ROC, создается впечатление, что модель довольно хороша.

Вот два разных способа построения ROC:

  1. (Используя https://stats.stackexchange.com/questions/188616/how-can-we-calculate-roc-auc-for-classification-algorithm-such-as-random-forest)

    library(pROC)
    rf.roc<-roc(RF_input_BV_clean$bv.disease, classify_BV_100t$votes[,2])
    plot(rf.roc)
    auc(rf.roc)
    
  2. (Используя Как вычислить ROC и AUC под ROC после обучения с использованием каретки в R?)

    library(ROCR)
    predictions <- as.vector(classify_BV_100t$votes[,2])
    pred <- prediction(predictions, RF_input_BV_clean$bv.disease)
    
    perf_AUC <- performance(pred,"auc") #Calculate the AUC value
    AUC <- [email protected][[1]]
    
    perf_ROC <- performance(pred,"tpr","fpr") #plot the actual ROC curve
    plot(perf_ROC, main="ROC plot")
    text(0.5,0.5,paste("AUC = ",format(AUC, digits=5, scientific=FALSE)))
    

Это графики ROC из 1 и 2:

Сюжет ROC 1

Сюжет ROC 2

Оба метода дают мне AUC 0,8621593.

Кто-нибудь знает, почему результаты матрицы путаницы случайного леса, похоже, не складываются с ROC / AUC?


person Alicia    schedule 20.11.2019    source источник


Ответы (2)


Я не верю, что с вашими графиками ROC что-то не так, и ваша оценка несоответствия верна.

Высокие значения AUC являются результатом очень высокой истинно отрицательной скорости. ROC учитывает чувствительность; в значительной степени мера истинно положительных ценностей и специфики; мера истинных отрицательных значений. Поскольку ваша специфичность очень высока, эта метрика фактически несет более низкое значение чувствительности модели, и это сохраняет ваш AUC относительно высоким. Да, у него высокий AUC, но, как вы упомянули, модель хороша только для прогнозирования негативов.

Я бы рекомендовал рассчитывать дополнительные метрики (чувствительность, специфичность, истинно положительный результат, ложный положительный результат ...) и оценивать комбинацию всех этих показателей, когда вы оцениваете свою модель. AUC - это показатель качества, но он означает гораздо больше с дополнительными показателями.

person carverd    schedule 20.11.2019

Чтобы добавить к ответу @ DanCarver, вы также можете изменить вероятность отсечения, при которой вы прогнозируете результат, как 0 или 1. По умолчанию оба порога вероятности в randomForest равны 0,5 для задачи с двумя классами. Однако, если, скажем, ложноотрицательный результат (неверный прогноз 0) дороже, чем ложный положительный результат (и неправильный прогноз 1), вы можете использовать более низкую вероятность отсечения для прогнозирования класса 1.

Вот пример использования данных BreastCancer:

library(randomForest)
library(mlbench)
data(BreastCancer)
library(caret)

# Limit data frame to complete cases
d = BreastCancer[complete.cases(BreastCancer),]

# Run random forest model
set.seed(10)
m1 = randomForest(Class ~ Bare.nuclei + Marg.adhesion, data=d)
m1

# Generate data frame of predictions
pred = data.frame(predict(m1, type="prob"), 
                  actual=d$Class, 
                  thresh0.5=predict(m1))

# Add prediction if we set probability threshold of 0.3 (instead of 0.5) 
# for classifying a prediction as "malignant"
pred$thresh0.3 = factor(ifelse(pred$malignant > 0.3, "malignant", "benign"))

# Look at confusion matrix for each probability threshold    
confusionMatrix(pred$thresh0.5, pred$actual)
confusionMatrix(pred$thresh0.3, pred$actual)

Ниже приведена часть вывода функции confusionMatrix. Обратите внимание, что с более низким порогом мы фиксируем больше истинных срабатываний (220 вместо 214), но за счет также получения большего количества ложных срабатываний (28 вместо 20). Это может быть хорошим компромиссом, если ложноотрицательный результат дороже, чем ложный положительный результат. В этой статье обсуждается настройка моделей randomForest для оптимизации порога вероятности.

Пороговая вероятность 0,5 для прогнозирования злокачественности

           Reference
Prediction  benign malignant
  benign       424        25
  malignant     20       214

Пороговая вероятность 0,3 для прогнозирования злокачественности

           Reference
Prediction  benign malignant
  benign       416        19
  malignant     28       220
person eipi10    schedule 20.11.2019