Στο συγκεκριμένο μέρος της ανάλυσης χρησιμοποιείται το dataset Breast Cancer Wisconsin, το οποίο περιλαμβάνει κυτταρολογικά χαρακτηριστικά από βιοψίες όγκων. Στόχος είναι η εκπαίδευση ενός Random Forest μοντέλου που προβλέπει αν ένας όγκος είναι καλοήθης ή κακοήθης. Η αξιολόγηση του μοντέλου γίνεται με βάση το accuracy, το sensitivity και το AUC, με ιδιαίτερη έμφαση στην αναγνώριση των κακοήθων περιπτώσεων.
Σε αυτό το βήμα, το dataset χωρίζεται σε training set και testing set
με αναλογία 70/30. Η διαδικασία γίνεται με stratified split, ώστε να
διατηρηθούν παρόμοιες οι αναλογίες των δύο κλάσεων, δηλαδή
benign και malignant, τόσο στο training όσο
και στο testing dataset.
library(tidyverse)
library(mlbench)
library(randomForest)
library(xgboost)
library(caret)
library(pROC)
set.seed(42)
# --- Φόρτωση δεδομένων ---
data("BreastCancer", package = "mlbench")
bc <- BreastCancer
# Καθαρισμός: αφαίρεση ID, χειρισμός missing, μετατροπή σε numeric
bc$Id <- NULL
bc <- na.omit(bc)
bc[, 1:9] <- lapply(bc[, 1:9], function(x) as.numeric(as.character(x)))
str(bc)
## 'data.frame': 683 obs. of 10 variables:
## $ Cl.thickness : num 5 5 3 6 4 8 1 2 2 4 ...
## $ Cell.size : num 1 4 1 8 1 10 1 1 1 2 ...
## $ Cell.shape : num 1 4 1 8 1 10 1 2 1 1 ...
## $ Marg.adhesion : num 1 5 1 1 3 8 1 1 1 1 ...
## $ Epith.c.size : num 2 7 2 3 2 7 2 2 2 2 ...
## $ Bare.nuclei : num 1 10 2 4 1 10 10 1 1 1 ...
## $ Bl.cromatin : num 3 3 3 3 3 9 3 3 1 2 ...
## $ Normal.nucleoli: num 1 2 1 7 1 7 1 1 1 1 ...
## $ Mitoses : num 1 1 1 1 1 1 1 1 5 1 ...
## $ Class : Factor w/ 2 levels "benign","malignant": 1 1 1 1 1 2 1 1 1 1 ...
## - attr(*, "na.action")= 'omit' Named int [1:16] 24 41 140 146 159 165 236 250 276 293 ...
## ..- attr(*, "names")= chr [1:16] "24" "41" "140" "146" ...
table(bc$Class)
##
## benign malignant
## 444 239
set.seed(42)
train_idx <- createDataPartition(bc$Class,p = 0.7,list = FALSE)
train <- bc[train_idx, ]
test <- bc[-train_idx, ]
# Έλεγχος ότι οι αναλογίες των κλάσεων διατηρήθηκαν
prop.table(table(train$Class)) %>% round(3)
##
## benign malignant
## 0.649 0.351
prop.table(table(test$Class)) %>% round(3)
##
## benign malignant
## 0.652 0.348
Το αποτέλεσμα δείχνει ότι οι αναλογίες των δύο κλάσεων είναι παρόμοιες στο training και στο testing dataset. Αυτό είναι σημαντικό, γιατί το μοντέλο πρέπει να εκπαιδευτεί και να αξιολογηθεί σε δεδομένα που έχουν παρόμοια κατανομή με το αρχικό dataset. Με αυτόν τον τρόπο, η αξιολόγηση του μοντέλου είναι πιο αξιόπιστη και δεν επηρεάζεται υπερβολικά από ανισορροπία μεταξύ των κλάσεων.
Σε αυτό το βήμα εκπαιδεύεται ένα μοντέλο Random Forest με στόχο την
πρόβλεψη της μεταβλητής Class, η οποία δείχνει αν ένας
όγκος είναι benign ή malignant. Το μοντέλο
χρησιμοποιεί όλα τα διαθέσιμα κυτταρολογικά χαρακτηριστικά του dataset
ως ανεξάρτητες μεταβλητές. Ο αριθμός των δέντρων ορίζεται σε 500, ενώ η
επιλογή importance = TRUE επιτρέπει αργότερα την ανάλυση
της σημαντικότητας των μεταβλητών.
set.seed(42)
rf_model <- randomForest(
Class ~ ., # Χρήση όλων των μεταβλητών για πρόβλεψη του Class
data = train,
ntree = 500, # Αριθμός δέντρων
importance = TRUE # Υπολογισμός variable importance
)
print(rf_model)
##
## Call:
## randomForest(formula = Class ~ ., data = train, ntree = 500, importance = TRUE)
## Type of random forest: classification
## Number of trees: 500
## No. of variables tried at each split: 3
##
## OOB estimate of error rate: 3.76%
## Confusion matrix:
## benign malignant class.error
## benign 301 10 0.03215434
## malignant 8 160 0.04761905
Το Random Forest εκπαιδεύτηκε χρησιμοποιώντας 500 decision trees. Κάθε δέντρο δημιουργείται με τυχαίο υποσύνολο των δεδομένων και των μεταβλητών, ενώ η τελική πρόβλεψη βασίζεται στη συνδυασμένη απόφαση όλων των δέντρων. Αυτή η διαδικασία βοηθά στη μείωση του variance και κάνει το μοντέλο πιο σταθερό και λιγότερο ευαίσθητο σε τυχαίες αλλαγές των δεδομένων.
Το output του μοντέλου εμφανίζει βασικές πληροφορίες, όπως τον αριθμό των δέντρων, τον αριθμό των μεταβλητών που εξετάζονται σε κάθε split και το OOB error rate. Το OOB error αποτελεί μια εσωτερική εκτίμηση του σφάλματος του μοντέλου, χωρίς να χρησιμοποιείται ξεχωριστό validation set.
Το παρακάτω διάγραμμα δείχνει πώς μεταβάλλεται το OOB error καθώς αυξάνεται ο αριθμός των δέντρων στο Random Forest. Αν η καμπύλη σταθεροποιείται, τότε σημαίνει ότι ο αριθμός των δέντρων είναι επαρκής και η προσθήκη περισσότερων δέντρων δεν βελτιώνει σημαντικά το μοντέλο.
plot(rf_model, main = "OOB Error vs Number of Trees")
legend(
"topright",
colnames(rf_model$err.rate),
col = 1:3,
lty = 1:3
)
Σε αυτό το βήμα χρησιμοποιείται το εκπαιδευμένο Random Forest μοντέλο
για να γίνουν προβλέψεις στο test set. Η αξιολόγηση γίνεται με Accuracy,
Sensitivity και AUC. Ως positive class ορίζεται η κλάση
malignant, επειδή στο συγκεκριμένο πρόβλημα μας ενδιαφέρει
ιδιαίτερα η σωστή αναγνώριση των κακοήθων περιπτώσεων.
# Προβλέψεις κλάσης
rf_pred <- predict(rf_model, test)
# Προβλέψεις πιθανοτήτων για την κλάση malignant
rf_prob <- predict(rf_model, test, type = "prob")[, "malignant"]
# Confusion Matrix
rf_cm <- confusionMatrix(rf_pred,test$Class,positive = "malignant")
print(rf_cm)
## Confusion Matrix and Statistics
##
## Reference
## Prediction benign malignant
## benign 131 2
## malignant 2 69
##
## Accuracy : 0.9804
## 95% CI : (0.9506, 0.9946)
## No Information Rate : 0.652
## P-Value [Acc > NIR] : <2e-16
##
## Kappa : 0.9568
##
## Mcnemar's Test P-Value : 1
##
## Sensitivity : 0.9718
## Specificity : 0.9850
## Pos Pred Value : 0.9718
## Neg Pred Value : 0.9850
## Prevalence : 0.3480
## Detection Rate : 0.3382
## Detection Prevalence : 0.3480
## Balanced Accuracy : 0.9784
##
## 'Positive' Class : malignant
##
# AUC
rf_auc <- roc(
test$Class,
rf_prob,
levels = c("benign", "malignant"),
quiet = TRUE
)$auc
cat("RF AUC:", round(rf_auc, 3), "\n")
## RF AUC: 0.999
# Συγκεντρωτικός πίνακας με τα βασικά metrics
rf_results <- tibble(
Model = "Random Forest",
Accuracy = round(rf_cm$overall["Accuracy"], 3),
Sensitivity = round(rf_cm$byClass["Sensitivity"], 3),
AUC = round(as.numeric(rf_auc), 3)
)
rf_results
## # A tibble: 1 × 4
## Model Accuracy Sensitivity AUC
## <chr> <dbl> <dbl> <dbl>
## 1 Random Forest 0.98 0.972 0.999
Το Random Forest μοντέλο αξιολογήθηκε στο test set και πέτυχε Accuracy = 0.980, δηλαδή περίπου 98.0%. Αυτό σημαίνει ότι ταξινόμησε σωστά το 98% των περιπτώσεων, άρα είχε πολύ υψηλή συνολική απόδοση.
Ωστόσο, σε ιατρικό context το Accuracy δεν είναι από μόνο του αρκετό.
Είναι σημαντικό να εξετάζεται και το Sensitivity,
επειδή δείχνει πόσο καλά το μοντέλο αναγνωρίζει τις πραγματικά κακοήθεις
περιπτώσεις (malignant). Ένα false negative, δηλαδή ένας
κακοήθης όγκος να προβλεφθεί ως καλοήθης, μπορεί να έχει σοβαρές
συνέπειες.
Επομένως, το 98.0% Accuracy είναι πολύ καλό αποτέλεσμα, αλλά πρέπει να αξιολογείται μαζί με το Sensitivity, το AUC και το confusion matrix.
Σε αυτό το βήμα παρουσιάζεται το Variable Importance plot του Random
Forest μοντέλου. Το γράφημα δείχνει ποιες μεταβλητές συνέβαλαν
περισσότερο στην πρόβλεψη της μεταβλητής Class.
varImpPlot(rf_model, main = "Variable Importance — Random Forest")
importance(rf_model)
## benign malignant MeanDecreaseAccuracy MeanDecreaseGini
## Cl.thickness 12.702656 19.830096 19.363837 11.845927
## Cell.size 11.605774 16.330563 19.826188 60.344346
## Cell.shape 10.417048 20.502944 21.800283 53.561147
## Marg.adhesion 6.228395 12.425305 13.009741 5.977215
## Epith.c.size 10.510480 3.579421 11.128863 11.709247
## Bare.nuclei 20.271034 19.036320 26.035566 34.154820
## Bl.cromatin 6.086543 14.621620 14.691182 14.587449
## Normal.nucleoli 11.849778 11.676750 15.229482 23.815034
## Mitoses 4.984157 0.839361 4.608274 1.550928
Με βάση το Variable Importance plot, τα τρία σημαντικότερα
χαρακτηριστικά του Random Forest μοντέλου ήταν τα
Cell.size, Cell.shape και
Bare.nuclei. Αυτές οι μεταβλητές είχαν τις μεγαλύτερες
τιμές σημαντικότητας και επομένως συνέβαλαν περισσότερο στη διάκριση
μεταξύ benign και malignant περιπτώσεων.
Το Cell.size και το Cell.shape σχετίζονται
με το μέγεθος και το σχήμα των κυττάρων, ενώ το Bare.nuclei
αφορά την παρουσία γυμνών πυρήνων. Η υψηλή σημαντικότητα αυτών των
χαρακτηριστικών είναι λογική, καθώς τέτοια κυτταρολογικά χαρακτηριστικά
μπορούν να βοηθήσουν στη διάκριση μεταξύ καλοήθων και κακοήθων
περιπτώσεων.
Σε αυτό το βήμα τα δεδομένα μετατρέπονται στην κατάλληλη μορφή για το
XGBoost. Σε αντίθεση με το Random Forest, το XGBoost δεν δέχεται
απευθείας data frames με factor target. Για αυτόν τον λόγο, οι
ανεξάρτητες μεταβλητές μετατρέπονται σε αριθμητικό matrix, ενώ η
μεταβλητή Class μετατρέπεται σε δυαδική μορφή, όπου
malignant = 1 και benign = 0.
# Μετατροπή των features σε numeric matrix
train_x <- as.matrix(train[, !names(train) %in% "Class"])
test_x <- as.matrix(test[, !names(test) %in% "Class"])
# Μετατροπή του target σε 0/1
# malignant = 1, benign = 0
train_y <- ifelse(train$Class == "malignant", 1, 0)
test_y <- ifelse(test$Class == "malignant", 1, 0)
# Δημιουργία xgb.DMatrix, δηλαδή της μορφής που χρειάζεται το XGBoost
dtrain <- xgb.DMatrix(data = train_x, label = train_y)
dtest <- xgb.DMatrix(data = test_x, label = test_y)
Η μετατροπή αυτή είναι απαραίτητη γιατί το XGBoost απαιτεί τα
δεδομένα εισόδου να είναι σε αριθμητική μορφή. Τα features αποθηκεύονται
ως matrices, ενώ η μεταβλητή-στόχος Class μετατρέπεται σε
δυαδικό vector. Η κλάση malignant ορίζεται ως 1, επειδή
αποτελεί τη θετική κλάση που θέλουμε να εντοπίζει το μοντέλο, ενώ η
κλάση benign ορίζεται ως 0.
Σε αυτό το βήμα εκπαιδεύεται ένα XGBoost μοντέλο για την πρόβλεψη της
κλάσης Class. Το μοντέλο χρησιμοποιεί objective
binary:logistic, επειδή το πρόβλημα είναι binary
classification, δηλαδή πρόβλεψη μεταξύ benign και
malignant. Ως μετρική αξιολόγησης χρησιμοποιείται το
AUC.
set.seed(42)
params <- list(
objective = "binary:logistic",
eval_metric = "auc",
max_depth = 4,
eta = 0.1,
subsample = 0.8,
colsample_bytree = 0.8
)
xgb_model <- xgb.train(
params = params,
data = dtrain,
nrounds = 500,
watchlist = list(train = dtrain, test = dtest),
early_stopping_rounds = 20,
print_every_n = 25,
verbose = 1,
maximize = TRUE
)
## Multiple eval metrics are present. Will use test_auc for early stopping.
## Will train until test_auc hasn't improved in 20 rounds.
##
## [1] train-auc:0.977109 test-auc:0.967489
## [26] train-auc:0.997722 test-auc:0.995446
## [51] train-auc:0.999541 test-auc:0.997458
## [76] train-auc:0.999847 test-auc:0.997564
## Stopping. Best iteration:
## [95] train-auc:0.999923 test-auc:0.997458
##
## [95] train-auc:0.999923 test-auc:0.997458
xgb_model$best_iteration
## NULL
xgb_model$best_score
## NULL
Το XGBoost μοντέλο εκπαιδεύτηκε με μέγιστο αριθμό 500 επαναλήψεων, αλλά χρησιμοποιήθηκε early stopping ώστε η εκπαίδευση να σταματήσει αν το AUC στο test set δεν βελτιωθεί για 20 συνεχόμενους γύρους. Αυτό βοηθά στην αποφυγή overfitting, επειδή το μοντέλο δεν συνεχίζει να εκπαιδεύεται άσκοπα όταν η απόδοσή του δεν βελτιώνεται.
Η παράμετρος max_depth = 4 ελέγχει το μέγιστο βάθος κάθε
δέντρου, ενώ το eta = 0.1 είναι το learning rate, δηλαδή το
πόσο γρήγορα μαθαίνει το μοντέλο σε κάθε επανάληψη. Οι παράμετροι
subsample = 0.8 και colsample_bytree = 0.8
σημαίνουν ότι το μοντέλο χρησιμοποιεί κάθε φορά ένα ποσοστό των
παρατηρήσεων και των μεταβλητών, κάτι που μπορεί να βοηθήσει στη μείωση
του overfitting.
Σε αυτό το βήμα συγκρίνονται τα δύο μοντέλα, Random Forest και XGBoost, με βάση τις μετρικές Accuracy, Sensitivity, Specificity και AUC. Η σύγκριση γίνεται στο test set, ώστε να αξιολογηθεί η απόδοση των μοντέλων σε δεδομένα που δεν χρησιμοποιήθηκαν στην εκπαίδευση.
# ==============================
# Random Forest metrics
# ==============================
rf_pred <- predict(rf_model, test)
rf_prob <- predict(rf_model, test, type = "prob")[, "malignant"]
rf_cm <- confusionMatrix(
rf_pred,
test$Class,
positive = "malignant"
)
rf_auc <- roc(
test$Class,
rf_prob,
levels = c("benign", "malignant")
)$auc
# ==============================
# XGBoost metrics
# ==============================
xgb_prob <- predict(xgb_model, dtest)
xgb_pred <- factor(
ifelse(xgb_prob > 0.5, "malignant", "benign"),
levels = levels(test$Class)
)
xgb_cm <- confusionMatrix(
xgb_pred,
test$Class,
positive = "malignant"
)
xgb_auc <- roc(
test$Class,
xgb_prob,
levels = c("benign", "malignant")
)$auc
# ==============================
# Comparison table
# ==============================
comparison_results <- tibble(
Model = c("Random Forest", "XGBoost"),
Accuracy = c(
rf_cm$overall["Accuracy"],
xgb_cm$overall["Accuracy"]
),
Sensitivity = c(
rf_cm$byClass["Sensitivity"],
xgb_cm$byClass["Sensitivity"]
),
Specificity = c(
rf_cm$byClass["Specificity"],
xgb_cm$byClass["Specificity"]
),
AUC = c(
as.numeric(rf_auc),
as.numeric(xgb_auc)
)
)
comparison_results <- comparison_results %>%
mutate(across(where(is.numeric), round, 3))
comparison_results
## # A tibble: 2 × 5
## Model Accuracy Sensitivity Specificity AUC
## <chr> <dbl> <dbl> <dbl> <dbl>
## 1 Random Forest 0.98 0.972 0.985 0.999
## 2 XGBoost 0.975 0.958 0.985 0.998
Από τη σύγκριση των δύο μοντέλων φαίνεται ότι τόσο το Random Forest όσο και το XGBoost πέτυχαν πολύ υψηλή απόδοση στην ταξινόμηση των όγκων σε καλοήθεις και κακοήθεις. Το Random Forest είχε Accuracy 0.980, δηλαδή περίπου 98.0%, Sensitivity 0.972, Specificity 0.985 και AUC 0.999. Αυτό δείχνει ότι το μοντέλο ταξινόμησε σωστά τη μεγάλη πλειοψηφία των περιπτώσεων του test set και είχε πολύ υψηλή ικανότητα αναγνώρισης των κακοήθων περιπτώσεων.
Το XGBoost παρουσίασε επίσης εξαιρετική απόδοση, με Accuracy 0.975,
Sensitivity 0.958, Specificity 0.985 και AUC 0.998. Η τιμή AUC δείχνει
ότι και αυτό το μοντέλο έχει πολύ ισχυρή ικανότητα διαχωρισμού μεταξύ
των δύο κλάσεων, δηλαδή benign και
malignant.
Συγκριτικά, το Random Forest ήταν το μοντέλο που νίκησε, αλλά με πολύ μικρή διαφορά. Συγκεκριμένα, είχε υψηλότερο Accuracy κατά 0.005, δηλαδή περίπου 0.5 ποσοστιαίες μονάδες, υψηλότερο Sensitivity κατά 0.014, δηλαδή περίπου 1.4 ποσοστιαίες μονάδες, και ελαφρώς υψηλότερο AUC κατά 0.001. Το Specificity ήταν ίδιο και για τα δύο μοντέλα, με τιμή 0.985.
Αυτό που προκαλεί ενδιαφέρον είναι ότι το XGBoost, παρόλο που είναι ένα πολύ ισχυρό boosting μοντέλο, δεν ξεπέρασε το Random Forest στο συγκεκριμένο dataset. Και τα δύο μοντέλα είχαν σχεδόν τέλεια απόδοση, με AUC πολύ κοντά στο 1, όμως το Random Forest είχε ελαφρώς καλύτερη συνολική απόδοση και υψηλότερο Sensitivity.
Σε ιατρικό context, το Sensitivity είναι ιδιαίτερα σημαντικό, επειδή δείχνει πόσο καλά το μοντέλο εντοπίζει τις πραγματικά κακοήθεις περιπτώσεις. Επομένως, με βάση τα συγκεκριμένα αποτελέσματα, το Random Forest μπορεί να θεωρηθεί ελαφρώς καλύτερη επιλογή, καθώς είχε την υψηλότερη ευαισθησία στην ανίχνευση κακοήθειας.
train_xgb_eta <- function(eta_value) {
params_eta <- list(
objective = "binary:logistic",
eval_metric = "auc",
max_depth = 4,
eta = eta_value
)
model_eta <- xgb.train(
params = params_eta,
data = dtrain,
nrounds = 500,
watchlist = list(
train = dtrain,
test = dtest
),
early_stopping_rounds = 20,
maximize = TRUE,
verbose = 0
)
# Παίρνουμε τα καλύτερα αποτελέσματα από τα attributes
best_iteration <- as.numeric(xgb.attr(model_eta, "best_iteration")) + 1
best_score <- as.numeric(xgb.attr(model_eta, "best_score"))
# Πόσοι γύροι έτρεξαν συνολικά μέχρι να σταματήσει
stopped_at <- nrow(model_eta$evaluation_log)
tibble(
eta = eta_value,
Best_Iteration = best_iteration,
Stopped_At = stopped_at,
Best_Test_AUC = best_score
)
}
eta_results <- bind_rows(
train_xgb_eta(0.01),
train_xgb_eta(0.10),
train_xgb_eta(0.3)
)
eta_results <- eta_results %>%
mutate(Best_Test_AUC = round(Best_Test_AUC, 4))
eta_results
## # A tibble: 3 × 3
## eta Best_Iteration Best_Test_AUC
## <dbl> <dbl> <dbl>
## 1 0.01 35 0.995
## 2 0.1 25 0.997
## 3 0.3 30 0.997
Από τη δοκιμή διαφορετικών τιμών του learning rate (eta)
παρατηρείται ότι τα XGBoost μοντέλα πέτυχαν πολύ υψηλή απόδοση. Στο
αρχικό μοντέλο χρησιμοποιήθηκε eta = 0.10, ενώ μετέπειτα
δοκιμάστηκαν επιπλέον οι τιμές eta = 0.01 και
eta = 0.30.
Για eta = 0.01, το καλύτερο αποτέλεσμα εμφανίστηκε στο
35ο iteration, με AUC 0.9950. Για eta = 0.30, το καλύτερο
αποτέλεσμα εμφανίστηκε στο 30ο iteration, με AUC 0.9972. Τα αποτελέσματα
δείχνουν ότι το μεγαλύτερο learning rate, δηλαδή
eta = 0.30, χρειάστηκε λιγότερους γύρους εκπαίδευσης για να
φτάσει στην καλύτερη απόδοσή του και πέτυχε ελαφρώς υψηλότερο AUC.
Αυτό είναι αναμενόμενο, καθώς ένα μεγαλύτερο eta
επιτρέπει στο μοντέλο να μαθαίνει πιο γρήγορα σε κάθε iteration.
Αντίθετα, ένα μικρότερο eta, όπως το 0.01, οδηγεί σε πιο
αργή και σταδιακή μάθηση, άρα συνήθως χρειάζεται περισσότερους γύρους
για να πετύχει την καλύτερη απόδοση.
Συνολικά, στο συγκεκριμένο dataset, το eta = 0.30
φαίνεται να ήταν ελαφρώς πιο αποδοτικό, καθώς πέτυχε καλύτερο AUC με
λιγότερα iterations. Ωστόσο, η διαφορά μεταξύ των τιμών είναι πολύ
μικρή, αφού τα AUC είναι πολύ κοντά στο 1. Αυτό σημαίνει ότι τα μοντέλα
είχαν εξαιρετική ικανότητα διάκρισης μεταξύ benign και
malignant περιπτώσεων.
Σε αυτό το βήμα δημιουργείται ένα ROC plot για τη σύγκριση του Random
Forest και του XGBoost. Το ROC curve δείχνει την ικανότητα κάθε μοντέλου
να διαχωρίζει τις δύο κλάσεις, δηλαδή benign και
malignant.
# ROC curves
roc_rf <- roc(
test$Class,
rf_prob,
levels = c("benign", "malignant")
)
roc_xgb <- roc(
test$Class,
xgb_prob,
levels = c("benign", "malignant")
)
# AUC values
rf_auc <- auc(roc_rf)
xgb_auc <- auc(roc_xgb)
# ROC plot
plot(
roc_rf,
col = "forestgreen",
lwd = 2,
main = "ROC Curves Comparison"
)
lines(
roc_xgb,
col = "steelblue",
lwd = 2
)
legend(
"bottomright",
legend = c(
paste0("RF (AUC = ", round(rf_auc, 3), ")"),
paste0("XGBoost (AUC = ", round(xgb_auc, 3), ")")
),
col = c("forestgreen", "steelblue"),
lwd = 2
)
Το ROC plot συγκρίνει την ικανότητα των δύο μοντέλων να διαχωρίζουν
τις benign από τις malignant περιπτώσεις. Όσο
πιο κοντά βρίσκεται η καμπύλη στην πάνω αριστερή γωνία, τόσο καλύτερη
είναι η διαχωριστική ικανότητα του μοντέλου.
Με βάση τα προηγούμενα αποτελέσματα, και τα δύο μοντέλα έχουν πολύ υψηλό AUC, γεγονός που δείχνει ότι μπορούν να ξεχωρίσουν με μεγάλη ακρίβεια τις καλοήθεις από τις κακοήθεις περιπτώσεις. Το Random Forest είχε AUC περίπου 0.999, ενώ το XGBoost είχε AUC περίπου 0.998. Επομένως, οι δύο καμπύλες αναμένεται να είναι πολύ κοντά μεταξύ τους, με το Random Forest να παρουσιάζει ελαφρώς υψηλότερη διαχωριστική ικανότητα.