Ο καρκίνος του μαστού αποτελεί την πιο συχνή μορφή καρκίνου στις γυναίκες παγκοσμίως (25% των περιπτώσεων). Ξεκινά από την ανεξέλεγκτη ανάπτυξη κυττάρων που σχηματίζουν όγκους. Το παρόν σύνολο δεδομένων (αναφορά από Kaggle) περιέχει χαρακτηριστικά τέτοιων κυττάρων. Ο βασικός στόχος της ανάλυσης είναι να χρησιμοποιήσουμε αλγορίθμους Μηχανικής Μάθησης για να ταξινομήσουμε επιτυχώς αυτούς τους όγκους σε Κακοήθεις (Malignant - M) ή Καλοήθεις (Benign - B).
Το αρχείο αποτελείται από τις εξής βασικές κατηγορίες πληροφοριών:
Μεταβλητή-Στόχος: Η στήλη diagnosis
που περιέχει την πραγματική διάγνωση (M ή B).
Χαρακτηριστικά (Features): 30 συνεχείς,
αριθμητικές μεταβλητές που καταγράφουν φυσικά και γεωμετρικά
χαρακτηριστικά των κυτταρικών πυρήνων (όπως ακτίνα, υφή, περίμετρος και
εμβαδόν). Η στήλη id (αναγνωριστικό ασθενούς) δεν έχει
αναλυτική αξία και αφαιρείται.
##
## Attaching package: 'dplyr'
## The following objects are masked from 'package:stats':
##
## filter, lag
## The following objects are masked from 'package:base':
##
## intersect, setdiff, setequal, union
Λόγω της ανομοιογένειας στις κλίμακες των μετρήσεων (π.χ. το εμβαδόν έχει τιμές >1000 ενώ άλλες μεταβλητές έχουν τιμές <0.1), είναι απαραίτητη η κανονικοποίηση (scaling) των 30 αριθμητικών μεταβλητών. Μόνο έτσι εξασφαλίζεται ότι οι αλγόριθμοι συσταδοποίησης θα λειτουργήσουν σωστά και αντικειμενικά.
# 1. Διαβάζουμε το αρχείο
breast_cancer <- read.csv("breast_cancer.csv")
# 2. Αφαιρούμε ΜΟΝΟ την 1η (id) στήλη και ΚΡΑΤΑΜΕ την diagnosis
breast_cancer$id = NULL
# 3. Βρίσκουμε ποιες στήλες είναι αριθμητικές (numeric)
numeric_columns <- sapply(breast_cancer, is.numeric)
# 4. Εφαρμόζουμε την scale() ΜΟΝΟ σε αυτές τις αριθμητικές στήλες
breast_cancer[numeric_columns] <- scale(breast_cancer[numeric_columns])
# Βλέπουμε το αποτέλεσμα
View(breast_cancer)Παίρνω κάθε ασθενή ως ένα μεμονωμένο σημείο. Ο αλγόριθμος μετράει αποστάσεις και ενώνει σταδιακά αυτούς που έχουν τα πιο όμοια κύτταρα (π.χ. παρόμοιο μέγεθος/ακτίνα). Οι μικρές ομάδες ενώνονται σε μεγαλύτερες, “χτίζοντας” την ιεραρχία από κάτω προς τα πάνω.
# 1. Υπολογισμός του πίνακα αποστάσεων (Ευκλείδεια απόσταση)
distances <- dist(breast_cancer[numeric_columns], method = "euclidean")
# 2. Εφαρμογή Ιεραρχικής Συσταδοποίησης (με τη μέθοδο Ward)
hc_model <- hclust(distances, method = "ward.D2")
# 3. Σχεδίαση του Δενδρογράμματος
plot(hc_model,
main = "Δενδρόγραμμα Καρκινικών Όγκων",
xlab = "Ασθενείς",
ylab = "Απόσταση (Ύψος)",
sub = "",
cex = 0.5)
# 4. Χωρίζουμε το δέντρο σε 2 βασικές ομάδες
rect.hclust(hc_model, k = 2, border = c("red", "blue"))Με την δημιουργία του Δενδρογράμματος “κόψαμε” το δέντρο στα δύο, παίρνοντας τις 2 τελικές ομάδες μας: τους Καλοήθεις και τους Κακοήθεις.
# 1. "Κόβουμε" το δέντρο σε 2 ομάδες (clusters) και αποθηκεύουμε το αποτέλεσμα
cluster_groups <- cutree(hc_model, k = 2)
# Μέση ακτίνα κυττάρων ανά ομάδα
tapply(breast_cancer$radius_mean, cluster_groups, mean)## 1 2
## 0.9181884 -0.4388225
Αναλύοντας τα κέντρα των συστάδων (cluster centroids), παρατηρούμε
ότι το χαρακτηριστικό radius_mean (μέση ακτίνα) παίζει
καθοριστικό ρόλο στον διαχωρισμό των δεδομένων. Συγκεκριμένα, η συστάδα
που αντιστοιχεί στα καλοήθη κύτταρα παρουσιάζει σημαντικά υψηλότερη μέση
τιμή ακτίνας σε σχέση με τη συστάδα των κακοήθων. Αυτό επιβεβαιώνει ότι
ο αλγόριθμος εντόπισε με επιτυχία το βιολογικό μοτίβο όπου τα καρκινικά
κύτταρα τείνουν να έχουν μεγαλύτερους πυρήνες, και το αξιοποίησε
μαθηματικά για να ομαδοποιήσει σωστά τα δεδομένα χωρίς να γνωρίζει εκ
των προτέρων την πραγματική διάγνωση.
## 1 2
## 0.9239069 -0.4415555
Αναλύοντας τα κέντρα των συστάδων (cluster centroids), παρατηρούμε
ότι το χαρακτηριστικό area_mean(Μέσο εμβαδόν) παίζει
καθοριστικό ρόλο στον διαχωρισμό των δεδομένων. Συγκεκριμένα, η συστάδα
που αντιστοιχεί στα καλοήθη κύτταρα παρουσιάζει σημαντικά υψηλότερη μέση
τιμή ακτίνας σε σχέση με τη συστάδα των κακοήθων. Αυτό επιβεβαιώνει ότι
ο αλγόριθμος εντόπισε με επιτυχία το βιολογικό μοτίβο όπου τα καρκινικά
κύτταρα τείνουν να έχουν μεγαλύτερους πυρήνες, και το αξιοποίησε
μαθηματικά για να ομαδοποιήσει σωστά τα δεδομένα χωρίς να γνωρίζει εκ
των προτέρων την πραγματική διάγνωση.
## radius_mean texture_mean perimeter_mean
## -0.43882252 -0.22519775 -0.45626175
## area_mean smoothness_mean compactness_mean
## -0.44155551 -0.30860095 -0.50439352
## concavity_mean concave.points_mean symmetry_mean
## -0.54604871 -0.55191476 -0.29624499
## fractal_dimension_mean radius_se texture_se
## -0.17372265 -0.40569174 -0.03880634
## perimeter_se area_se smoothness_se
## -0.40660638 -0.38063043 -0.06525941
## compactness_se concavity_se concave.points_se
## -0.35485830 -0.32039096 -0.38611774
## symmetry_se fractal_dimension_se radius_worst
## -0.06638193 -0.24826781 -0.47170196
## texture_worst perimeter_worst area_worst
## -0.23542610 -0.48486644 -0.46295015
## smoothness_worst compactness_worst concavity_worst
## -0.31960678 -0.44331378 -0.49227774
## concave.points_worst symmetry_worst fractal_dimension_worst
## -0.53818434 -0.25648857 -0.31310737
Η Μαζική ανάλυση χαρακτηριστικών δείχνει το “τυπικό προφίλ” ενός κακοήθους όγκου για όλες τις παραμέτρους (ακτίνα, υφή, εμβαδόν κ.λπ.). Παρατηρούμε ότι
Υποθέτουμε ότι θέλουμε να δούμε την περίπτωση ενός συγκεκριμένου ασθενή (π.χ. αυτού που βρίσκεται στη γραμμή 100 του αρχείου).
## [1] 2
Αυτός ο νέος ασθενής μοιάζει με τους ασθενείς του Cluster 2, άρα πρέπει να προσέξουμε γιατί το Cluster 2 έχει υψηλά ποσοστά κακοήθειας
Για να βρεις όλους τους “παρόμοιους” ασθενείς που ανήκουν στην ίδια ομάδα:
## [1] "M"
# Δημιουργούμε ένα νέο υποσύνολο με όλους τους ασθενείς της Ομάδας 2
similar_cases <- subset(breast_cancer, cluster_groups == 2)
# Βλέπουμε τους πρώτους 10 ασθενείς που είναι "όμοιοι" μεταξύ τους
head(similar_cases)## diagnosis radius_mean texture_mean perimeter_mean area_mean
## 11 M 0.5370834 0.9184652 0.4416221 0.40609593
## 12 M 0.4689800 -0.3254213 0.4786607 0.35835701
## 14 M 0.4888435 1.0835417 0.4827761 0.36318774
## 17 M 0.1568390 0.1953835 0.1140363 0.08414239
## 20 B -0.1666526 -1.1461538 -0.1855647 -0.25173500
## 21 B -0.2971842 -0.8322759 -0.2608765 -0.38330119
## smoothness_mean compactness_mean concavity_mean concave.points_mean
## 11 -1.01679116 -0.71291456 -0.7000684 -0.40432978
## 12 0.05259614 0.47070096 0.1347304 0.44174220
## 14 -0.87814055 -0.07840879 0.1327234 0.12166258
## 17 0.16422766 -0.61237067 -0.1862688 0.09460271
## 20 0.10165712 -0.43646621 -0.2779650 -0.02858414
## 21 0.79206608 0.42904436 -0.5408858 -0.45922267
## symmetry_mean fractal_dimension_mean radius_se texture_se perimeter_se
## 11 -1.0345653 -0.8253981 -0.092574387 -0.05411677 -0.19786746
## 12 0.1108232 -0.2801003 0.362868097 -0.42047331 0.34519831
## 14 0.1290618 -1.3338705 -0.006750704 -0.25170639 0.01827074
## 17 -0.8229967 -0.5067176 0.243508270 0.04195892 0.16269260
## 20 0.2676757 -0.7276694 -0.487796052 -0.77631592 -0.39966239
## 21 0.5667899 0.7524245 -0.793227393 -0.85045734 -0.73351430
## area_se smoothness_se compactness_se concavity_se concave.points_se
## 11 0.003801211 -1.0031510 -0.9051249 -0.6918331 -0.6815142
## 12 0.303860527 -0.4229713 0.8449693 -0.1319721 0.1659345
## 14 -0.082589493 0.9085778 0.3228615 0.6167179 1.3166106
## 17 0.111294988 -0.4406231 -0.7738441 -0.3946761 -0.1144416
## 20 -0.368799918 0.4732765 -0.6074397 -0.2658087 0.2194166
## 21 -0.564223164 -0.9805034 -0.3628587 -0.4940597 -0.8599501
## symmetry_se fractal_dimension_se radius_worst texture_worst perimeter_worst
## 11 -0.71885213 -0.2845365 0.6043170 1.3345970 0.4921886
## 12 -0.05592523 0.1319300 0.8588046 0.2607728 0.8701362
## 14 1.12113292 -0.2996533 0.1181009 0.3225990 0.1410247
## 17 -0.77933816 -0.6462048 0.5794890 0.8464951 0.4802847
## 20 -0.08979741 -0.5649523 -0.2398369 -1.0440863 -0.2250191
## 21 -0.45513304 -0.5177124 -0.3660462 -0.8439645 -0.3324514
## area_worst smoothness_worst compactness_worst concavity_worst
## 11 0.473194982 -0.62492667 -0.6302737 -0.60533934
## 12 0.734893708 0.31671645 1.9489119 0.59586313
## 14 -0.007171473 -0.84391344 -0.3932021 -0.19167703
## 17 0.452118574 0.61453846 -0.4268879 0.09208668
## 20 -0.297498987 0.50942481 -0.4891748 -0.15908255
## 21 -0.439237827 -0.05118133 0.1483124 -0.39874785
## concave.points_worst symmetry_worst fractal_dimension_worst
## 11 -0.22601086 0.0763637 0.03179084
## 12 1.01006256 1.4405702 1.15463563
## 14 -0.04117035 -0.1483101 -1.16690689
## 17 0.70427701 0.2072887 -0.09887552
## 20 0.21593293 0.1232381 -0.62873867
## 21 -0.63555051 0.4578243 -0.11714666
Παρατηρούμε ότι “παρόμοιες” περιπτώσεις είναι στισ γραμμές 11,12,14,17,20,21.
# 1. Ορίζουμε τον "σπόρο" (seed) για να έχουμε σταθερά τυχαία αρχικά κέντρα
set.seed(123)
# 2. Εκτελούμε τον αλγόριθμο K-means ΜΟΝΟ στα αριθμητικά δεδομένα
# centers = 2 (αφού ψάχνουμε Καλοήθη/Κακοήθη)
# nstart = 25 (η R θα δοκιμάσει 25 διαφορετικά τυχαία ξεκινήματα και θα κρατήσει το πιο σταθερό)
kmeans_model <- kmeans(breast_cancer[numeric_columns], centers = 2, nstart = 25)
# 3. Βλέπουμε το μέγεθος της κάθε ομάδας (πόσα κύτταρα μπήκαν πού)
kmeans_model$size## [1] 189 380
## radius_mean texture_mean perimeter_mean area_mean smoothness_mean
## 1 0.9731199 0.4810905 1.0057496 0.9626801 0.6087185
## 2 -0.4839991 -0.2392792 -0.5002281 -0.4788067 -0.3027573
## compactness_mean concavity_mean concave.points_mean symmetry_mean
## 1 1.0197987 1.138428 1.1635583 0.6106013
## 2 -0.5072157 -0.566218 -0.5787172 -0.3036938
## fractal_dimension_mean radius_se texture_se perimeter_se area_se
## 1 0.2520081 0.8578415 0.04270321 0.8595226 0.8063982
## 2 -0.1253409 -0.4266633 -0.02123923 -0.4274994 -0.4010770
## smoothness_se compactness_se concavity_se concave.points_se symmetry_se
## 1 0.01704563 0.6944395 0.6363352 0.7755561 0.1402588
## 2 -0.00847796 -0.3453923 -0.3164930 -0.3857371 -0.0697603
## fractal_dimension_se radius_worst texture_worst perimeter_worst area_worst
## 1 0.4146673 1.039169 0.5058654 1.0650336 1.0022723
## 2 -0.2062424 -0.516850 -0.2516015 -0.5297141 -0.4984986
## smoothness_worst compactness_worst concavity_worst concave.points_worst
## 1 0.6077580 0.9500013 1.0433804 1.145203
## 2 -0.3022796 -0.4725007 -0.5189444 -0.569588
## symmetry_worst fractal_dimension_worst
## 1 0.5968910 0.6219221
## 2 -0.2968747 -0.3093244
# 5. Πίνακας σύγκρισης (Συστάδες vs Πραγματική Διάγνωση)
table(Algorithm = kmeans_model$cluster, Reality = breast_cancer$diagnosis)## Reality
## Algorithm B M
## 1 14 175
## 2 343 37
Ο K-means πέτυχε έναν εξίσου εντυπωσιακό διαχωρισμό
Συγκεκριμένα, η Συστάδα 1 απομόνωσε τους Κακοήθεις όγκους (175 σωστές προβλέψεις, 14 λάθη), ενώ η Συστάδα 2 συγκέντρωσε τους Καλοήθεις (343 σωστές προβλέψεις, 37 λάθη).
Παρατηρούμε ότι τα αποτελέσματα των δύο αλγορίθμων είναι εξαιρετικά κοντινά, αποδεικνύοντας τη σταθερότητα των δεδομένων.
Η ανάλυση αποδεικνύει τη δύναμη τις Unsupervised Learning. Παρόλο που
“κρύψαμε” την πραγματική διάγνωση (diagnosis) από τους
αλγορίθμους, εκείνοι μπόρεσαν να ανακαλύψουν από μόνοι τους τα
υποκείμενα μοτίβα. Αποκλειστικά και μόνο μετρώντας μαθηματικές
αποστάσεις μεταξύ βιολογικών χαρακτηριστικών (όπως η ακτίνα και το
εμβαδόν), το σύστημα κατόρθωσε να διαχωρίσει τα υγιή από τα άρρωστα
κύτταρα με ποσοστό επιτυχίας που ξεπερνά το 90%