-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathDecisionTree.py
More file actions
84 lines (60 loc) · 3.86 KB
/
DecisionTree.py
File metadata and controls
84 lines (60 loc) · 3.86 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
from Imports import np, accuracy_score, classification_report, cross_validate, RANDOM_STATE
from Shared_Utilities import chose_dataset, print_confusion_matrix, Colors
from sklearn.tree import DecisionTreeClassifier
# -- -- # -- -- # -- -- # -- -- # -- -- # -- -- # -- -- #
def decision_tree_main(dataset, depth=10, criterion="entropy", votazione="none", show_results=True):
'''
Funzione per addestrare il DecisionTree in base al dataset scelto.
Parametri:
- dataset: tupla contenente i dati di training e di test già splittati.
- depth: profondità dell'albero (default: 10).
- criterion: criterio di split (default: entropy).
- votazione: tipologia di votazione da utilizzare
- none: il modello non fa parte di un ensemble (default).
- hard: il modello fa parte di un esemble e restituisce le sue predizioni.
- soft: il modello fa parte di un esemble e restituisce le probabilità delle sue predizioni.
- show_results: se True, stampa i risultati del classificatore (default = True).
'''
X_train, X_test, y_train, y_test = dataset # recupero dei dati
clf = DecisionTreeClassifier(max_depth=depth, criterion=criterion, random_state=RANDOM_STATE)
clf.fit(X_train, y_train) # addestramento del modello
classi = clf.classes_
y_pred = clf.predict(X_test) # previsioni sul test set
accuracy = accuracy_score(y_test, y_pred) # calcolo dell'accuratezza
if votazione == "hard":
return accuracy, y_pred
elif votazione == "soft":
probabilita = clf.predict_proba(X_test)
return accuracy, np.array([dict(zip(classi, probs)) for probs in probabilita])
# restituisce l'accuratezza e un array di dizionari con le probabilità di appartenenza ad ogni classe
elif show_results:
report = classification_report(y_test, y_pred) # report di classificazione
print(f'{Colors.GREEN}Accuratezza{Colors.RESET}: {accuracy:.3}')
print('\nReport sulle performance:')
print(report)
print_confusion_matrix(y_test, y_pred) # stampa della matrice di confusione
input(f"\nPremere {Colors.ORNG}INVIO{Colors.RESET} per continuare . . .")
return accuracy
# -- -- # -- -- # -- -- # -- -- # -- -- # -- -- # -- -- #
def tuning_iperparametri():
'''Funzione per il tuning degli iperparametri del Decision Tree.'''
# iperparametri da testare
criterions = ['gini', 'entropy'] ; all_depths = [i for i in range(1, 21)]
# menu interattivo per scelta del dataset da usare per il tuning
X_train, _, y_train, _ = chose_dataset()
# matrice per salvare tutti i risultati delle accuratezze
accuracies = np.zeros((len(criterions), len(all_depths)))
# for annidati per testare tutte le combinazioni di iperparametri
for i, criterion in enumerate(criterions):
for j, depth in enumerate(all_depths):
Tree = DecisionTreeClassifier(max_depth=depth, criterion=criterion, random_state=RANDOM_STATE)
all_scores = cross_validate(estimator=Tree, X=X_train, y=y_train, cv=10, n_jobs=10)
accuracies[i][j] = all_scores['test_score'].mean()
print("Criterio: \"{}\", profondità: {} - Accuratezza: {:.5f}".format(criterion, depth, accuracies[i][j]))
print("\n")
# indice della combinazione di iperparametri con l'accuratezza più alta
i,j = np.unravel_index(np.argmax(accuracies, axis=None), accuracies.shape)
print(f"Miglior {Colors.GREEN}Accuratezza{Colors.RESET}: %.5f (Usando criterio \"%s\" e profondita' \"%s\")" % (accuracies[i][j], criterions[i], all_depths[j]) )
# -- -- # -- -- # -- -- # -- -- # -- -- # -- -- # -- -- #
if __name__ == '__main__':
tuning_iperparametri()