Как CareT рассчитывает чувствительность и специфичность в образцах? - PullRequest
0 голосов
/ 27 сентября 2018

Недавно, когда я использовал пакет caret для запуска моей модели, я обнаружил, что чувствительность и специфичность при повторной выборке объекта поезда отличаются от вычисленных вручную для каждой складки.Позвольте мне использовать данные GermanCredit в качестве примера.

library(caret)
data("GermanCredit")
form = as.formula('credit_risk~amount+savings+installment_rate+age+housing+number_credits')
train.control <- trainControl(method="cv", 
                           number=5,
                           summaryFunction = twoClassSummary,
                           classProbs = TRUE,
                           savePredictions='all')
rf = train(form, data=GermanCredit,  method = 'rf',
           metric = 'ROC', trControl=train.control)

print(rf$resample)

Мы получили:

ROC         Sens        Spec        Resample
0.6239881   0.9428571   0.13333333  Fold1   
0.6603571   0.9714286   0.08333333  Fold2   
0.6622619   0.9642857   0.06666667  Fold5   
0.6502381   0.9928571   0.10000000  Fold4   
0.7072619   0.9714286   0.16666667  Fold3

Как видите, для сгиба 1 чувствительность и специфичность составляют 0,94 и 0,13 соответственно.

Теперь, если мы просто возьмем повторные выборки из Fold1 и используем confusionMatrix для вычисления метрик, мы получим следующий результат:

resamp.1 = rf$pred %>% filter(Resample=='Fold1')
cm=confusionMatrix(resamp.1$pred, resamp.1$obs)
print(cm) 

Confusion Matrix and Statistics

          Reference
Prediction good bad
      good  366 135
      bad    54  45

               Accuracy : 0.685          
                 95% CI : (0.6462, 0.722)
    No Information Rate : 0.7            
    P-Value [Acc > NIR] : 0.8018         

                  Kappa : 0.1393         
 Mcnemar's Test P-Value : 5.915e-09      

            Sensitivity : 0.8714         
            Specificity : 0.2500         
         Pos Pred Value : 0.7305         
         Neg Pred Value : 0.4545         
             Prevalence : 0.7000         
         Detection Rate : 0.6100         
   Detection Prevalence : 0.8350         
      Balanced Accuracy : 0.5607         

       'Positive' Class : good

Как вы можете заметить, чувствительность и специфичность составляют 0,87 и 0,25.соответственно.По сравнению с результатами, полученными в результате повторной выборки, цифры совершенно разные !!То же самое происходит с другими складками.

Я что-то не так сделал?Или карет делает что-то по-другому?Спасибо.

1 Ответ

0 голосов
/ 02 октября 2018

Обратите внимание, что data(GermanCredit) не имеет тех же переменных, что и те, которые вы сохраняете в form, это поможет при следующих вопросах, которые вы опубликуете в воспроизводимом примере.Также это поможет использовать set.seed().

Тем не менее, проблема заключается в том, что вам необходимо учитывать mtry, то есть количество «случайно выбранных предикторов», используемых в модели случайного леса. См. Документацию и код здесь .

Я настроил GermanCredit, чтобы каждый мог запустить его как есть:

library(caret)
data("GermanCredit")
form = as.formula('Class~Amount+SavingsAccountBonds.100.to.500+SavingsAccountBonds.lt.100+SavingsAccountBonds.500.to.1000+
SavingsAccountBonds.lt.100+SavingsAccountBonds.gt.1000+SavingsAccountBonds.Unknown+
                  InstallmentRatePercentage+Age+Housing.ForFree+Housing.Own+Housing.Rent+NumberExistingCredits')
train.control <- trainControl(method="cv", 
                              number=5,
                              summaryFunction = twoClassSummary,
                              classProbs = TRUE,
                              savePredictions='all')

set.seed(100)
rf <- train(form, data=GermanCredit,  method = 'rf',
           metric = 'ROC', trControl=train.control)

Если мы проверим rf, мыможно увидеть, что конечное значение mtry, использованное в модели, было mtry = 2.

> rf
Random Forest 

1000 samples
  12 predictor
   2 classes: 'Bad', 'Good' 

No pre-processing
Resampling: Cross-Validated (5 fold) 
Summary of sample sizes: 800, 800, 800, 800, 800 
Resampling results across tuning parameters:

  mtry  ROC        Sens        Spec     
   2    0.6465714  0.06333333  0.9842857
   7    0.6413214  0.31333333  0.8571429
  12    0.6358214  0.31666667  0.8385714

ROC was used to select the optimal model using the largest value.
The final value used for the model was mtry = 2.

Поэтому, отфильтровав mtry = 2 в rf$pred, вы получите ожидаемоерезультат.

resamp.1 <- rf$pred %>% filter(Resample=='Fold1' & mtry == 2)
cm <- confusionMatrix(resamp.1$pred, resamp.1$obs)
print(cm) 
Confusion Matrix and Statistics

          Reference
Prediction Bad Good
      Bad    7    5
      Good  53  135

               Accuracy : 0.71            
                 95% CI : (0.6418, 0.7718)
    No Information Rate : 0.7             
    P-Value [Acc > NIR] : 0.4123          

                  Kappa : 0.1049          
 Mcnemar's Test P-Value : 6.769e-10       

            Sensitivity : 0.1167          
            Specificity : 0.9643          
         Pos Pred Value : 0.5833          
         Neg Pred Value : 0.7181          
             Prevalence : 0.3000          
         Detection Rate : 0.0350          
   Detection Prevalence : 0.0600          
      Balanced Accuracy : 0.5405          

       'Positive' Class : Bad  

 cm$byClass[1:2] == rf$resample[1,2:3]
  Sens Spec
  TRUE TRUE

РЕДАКТИРОВАТЬ:

Вы также можете контролировать это, проверяя rf$resampledCM, и увидеть количество наблюдений в разных ячейках дляразные mtry и складки.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...