UNIVERSITÀ DEGLI STUDI DI GENOVA
FACOLTÀ DI INGEGNERIA
Corso di Laurea Specialistica in Ingegneria Gestionale
Dispense per le esercitazioni dell’insegnamento
Business Intelligence
Prof. Davide Anguita
A cura di:
Alessandro Ghio
[email protected]
Anno Accademico 2008 - 2009
Documento realizzato in LATEX
Indice
Prefazione
5
Principali acronimi utilizzati
7
1 Introduzione
1.1 Cos’è il Data Mining? . . . . . . . . . . .
1.2 Terminologia di base . . . . . . . . . . .
1.3 Data Mining Process . . . . . . . . . . .
1.3.1 Definizione degli obiettivi . . . .
1.3.2 Organizzazione dei dati . . . . . .
1.3.3 Analisi esplorativa dei dati . . . .
1.3.4 Scelta delle metodologie di analisi
1.3.5 Analisi dei dati . . . . . . . . . .
1.3.6 Valutazione dei metodi statistici e
1.3.7 Implementazione dell’algoritmo .
1.4 Il software che useremo: WEKA . . . . .
1.5 Organizzazione della dispensa . . . . . .
2 Organizzazione dei dati
2.1 Tipi di attributi . . . . . . . .
2.1.1 Variabili qualitative . .
2.1.2 Variabili quantitative .
2.2 La matrice dei dati . . . . . .
2.2.1 Gestione delle variabili
2.3 Normalizzazione di un dataset
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
. .
. .
. .
. .
. .
. .
. .
. .
dei
. .
. .
. .
.
.
.
.
.
.
.
.
.
.
.
.
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
risultati
. . . . .
. . . . .
. . . . .
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
ottenuti
. . . . .
. . . . .
. . . . .
9
9
12
14
14
15
15
19
20
20
21
21
24
.
.
.
.
.
.
25
25
26
26
27
28
29
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
3 Analisi esplorativa dei dati
31
3.1 Distribuzioni di frequenza . . . . . . . . . . . . . . . . . . . . 31
1
3.2
3.3
3.4
3.5
3.6
3.1.1 Distribuzioni univariate . . . . . . . . . . . . . .
3.1.2 Distribuzioni bivariate e multivariate . . . . . . .
Analisi esplorativa univariata . . . . . . . . . . . . . . .
3.2.1 Richiami su stimatori e loro caratteristiche . . . .
3.2.2 Indici di posizione . . . . . . . . . . . . . . . . . .
3.2.3 Indici di variabilità . . . . . . . . . . . . . . . . .
3.2.4 Indici di eterogeneità . . . . . . . . . . . . . . . .
Analisi esplorativa bivariata e multivariata . . . . . . . .
Esempi di analisi con WEKA . . . . . . . . . . . . . . .
Riduzione di dimensionalità . . . . . . . . . . . . . . . .
Esempi di riduzione di dimensionalità utilizzando WEKA
4 Classificazione
4.1 Zero Rules . . . . . . . . . . . . . . . . . . . .
4.1.1 Apprendimento . . . . . . . . . . . . .
4.1.2 Fase in avanti . . . . . . . . . . . . . .
4.1.3 Estensione al caso multiclasse . . . . .
4.1.4 Esempio di analisi in WEKA . . . . . .
4.2 Naive Bayesian Classifier . . . . . . . . . . . .
4.2.1 Apprendimento . . . . . . . . . . . . .
4.2.2 Fase in avanti . . . . . . . . . . . . . .
4.2.3 Estensione al caso multiclasse . . . . .
4.2.4 Esempio di analisi in WEKA . . . . . .
4.3 Reti neurali: MultiLayer Perceptrons . . . . .
4.3.1 Cenni storici: il percettrone . . . . . .
4.3.2 Architettura di un MLP . . . . . . . .
4.3.3 Apprendimento . . . . . . . . . . . . .
4.3.4 Fase in avanti . . . . . . . . . . . . . .
4.3.5 Estensione al caso multiclasse . . . . .
4.3.6 Esempio di analisi in WEKA (I) . . . .
4.3.7 Esempio di analisi in WEKA (II) . . .
4.3.8 Validation set e test set . . . . . . . .
4.4 Support Vector Machines . . . . . . . . . . . .
4.4.1 Il problema del classificatore a massimo
4.4.2 Apprendimento . . . . . . . . . . . . .
4.4.3 Fase in avanti . . . . . . . . . . . . . .
2
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
. . . . .
margine
. . . . .
. . . . .
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
31
32
33
33
34
35
36
38
40
43
44
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
48
49
49
49
49
49
54
54
55
55
56
56
56
60
62
64
64
64
66
67
68
68
71
73
4.4.4 Estensione al caso multiclasse . . .
4.4.5 SVM e la probabilità . . . . . . . .
4.4.6 Esempio di analisi in WEKA . . . .
4.4.7 SVM per feature selection . . . . .
4.5 Decision Trees . . . . . . . . . . . . . . . .
4.5.1 La nascita degli alberi di decisione
4.5.2 Apprendimento . . . . . . . . . . .
4.5.3 Fase in avanti . . . . . . . . . . . .
4.5.4 Estensione al caso multiclasse . . .
4.5.5 Esempio di analisi in WEKA . . . .
5 Regressione
5.1 Zero Rules . . . . . . . . . . . . . . .
5.1.1 Apprendimento . . . . . . . .
5.1.2 Fase in avanti . . . . . . . . .
5.1.3 Esempio di analisi in WEKA .
5.2 Support Vector Regression . . . . . .
5.2.1 Apprendimento . . . . . . . .
5.2.2 Fase in avanti . . . . . . . . .
5.2.3 Esempio di analisi in WEKA .
5.3 Regression Trees . . . . . . . . . . .
5.3.1 Apprendimento . . . . . . . .
5.3.2 Fase in avanti . . . . . . . . .
5.3.3 Esempio di analisi in WEKA .
6 Clustering
6.1 k–Means . . . . . . . . . . . . . . . .
6.1.1 Apprendimento . . . . . . . .
6.1.2 Fase in avanti . . . . . . . . .
6.1.3 Esempio di analisi in WEKA .
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
7 Association rules
7.1 Apriori . . . . . . . . . . . . . . . . . . .
7.1.1 Apprendimento . . . . . . . . . .
7.1.2 Esempio di analisi in WEKA (I) .
7.1.3 Esempio di analisi in WEKA (II)
3
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
73
74
75
76
80
80
82
86
86
87
.
.
.
.
.
.
.
.
.
.
.
.
90
90
90
90
91
91
92
93
93
93
93
94
94
.
.
.
.
.
.
.
.
96
96
97
98
98
.
.
.
.
100
. 101
. 101
. 104
. 106
.
.
.
.
.
.
.
.
.
.
.
.
8 Valutazione comparativa di algoritmi di Data Mining
8.1 Metodi (pratici) per la comparazione fra algoritmi . . .
8.1.1 Training set (TS) . . . . . . . . . . . . . . . . .
8.1.2 Validation set (VS) . . . . . . . . . . . . . . . .
8.1.3 K–Fold Cross Validation (KCV) . . . . . . . . .
8.2 Analisi in WEKA explorer . . . . . . . . . . . . . . . .
8.2.1 Metodo TS . . . . . . . . . . . . . . . . . . . .
8.2.2 Metodo VS . . . . . . . . . . . . . . . . . . . .
8.2.3 Metodo KCV . . . . . . . . . . . . . . . . . . .
8.3 Analisi in WEKA KF . . . . . . . . . . . . . . . . . . .
8.3.1 Input . . . . . . . . . . . . . . . . . . . . . . . .
8.3.2 Selezione della classe . . . . . . . . . . . . . . .
8.3.3 Creazione delle k fold per la KCV . . . . . . . .
8.3.4 Inserimento dei blocchi per le SVM . . . . . . .
8.3.5 Elaborazione dei risultati . . . . . . . . . . . . .
8.3.6 Uscita a video . . . . . . . . . . . . . . . . . . .
8.3.7 Configurazione finale ed esecuzione . . . . . . .
8.4 Note conclusive . . . . . . . . . . . . . . . . . . . . . .
Bibliografia
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
108
. 108
. 108
. 109
. 109
. 110
. 110
. 111
. 111
. 112
. 113
. 113
. 113
. 113
. 114
. 114
. 114
. 115
117
4
Prefazione
Il termine Business Intelligence (BI ) è piuttosto vago. Una definizione
che comunemente può essere rintracciata in letteratura [14] è la seguente:
Con il termine business intelligence (BI) ci si può solitamente
riferire a: un insieme di processi aziendali per raccogliere ed analizzare informazioni strategiche; la tecnologia utilizzata per realizzare questi processi; le informazioni ottenute come risultato di
questi processi.
Per quanto abbia riscosso sempre maggiore interesse solo negli ultimi
anni, il processo di BI venne definito come tale nel 1958 da H. P. Luhn,
ricercatore dell’IBM: ovviamente, all’epoca non si avevano a disposizione
gli strumenti di oggi (a partire dal computer stesso, almeno nell’accezione
moderna di PC), ma già era nata l’idea che i dati, specialmente quando sono
numerosi, debbano essere interpretati al fine di fornire informazioni utili. Non
solo: le stesse informazioni devono essere a loro volta analizzate per trovare
indici (quanto più completi e sintetici) in grado di velocizzare il processo
decisionale.
È immediato, quindi, comprendere come una parte fondamentale del processo di BI sia costituita dal Data Mining (DM ). Traducendo letteralmente
il termine Mining, esso deriva da to mine, ovvero estrarre (come si fa, nella
pratica, in miniera) risorse preziose dalle viscere dei (numerosi, in generale)
dati a disposizione. Proprio per questo motivo, al Data Mining viene spesso affiancato il concetto di Knowledge Discovery (KD): è quindi frequente
sentire parlare non solo di DM, ma, più in generale, di KDDM.
Nel corso di questo insegnamento vedrete che il DM fa parte di un processo molto complesso, che comprende progettazione ed interrogazione di database, creazione di Data Marts, reportistica, ecc. Durante le esercitazioni,
data l’esiguità del tempo a nostra disposizione, ci concentreremo solamente
5
sulla presentazione dei principali algoritmi di DM per BI: sia, quindi, ben
chiaro che:
• queste esercitazioni (sfortunatamente) non potranno coprire per intero
il problema della BI;
• verranno presentati solo alcuni algoritmi (i più famosi ed usati, seppure
in moltissime varianti che non analizzeremo), scelti tra la miriade di
tecniche a disposizione in letteratura.
Per queste dispense, ho tratto ispirazione da [10], sebbene Wikipedia1
offra sempre ottimi spunti di approfondimento.
1
http://wikipedia.it/
6
Principali acronimi utilizzati
Acronimo
BI
DM
KD
KDDM
MBA
ML
MLP
NN
SLT
SVM
NBC
IT
OLAP
KF
CV
IQR
PCA
SVD
MAE
RMSE
TP
FP
CM
Significato
Business Intelligence
Data Mining
Knowledge Discovery
Knowledge Discovery & Data Mining
Market Basket Analysis
Machine Learning
MultiLayer Perceptrons
Neural Networks (reti neurali)
Statistical Learning Theory
Support Vector Machine
Naive Bayesian Classifier
Information Technology
OnLine Analytical Processing
Knowledge Flow (programma di WEKA)
Coefficiente di variazione
Inter–Quartile Range
Principal Component Analysis
Singular Value Decomposition
Mean Absolute Error
Root Mean Squared Error
True Positives
False Positives
Confusion Matrix
7
Acronimo
BP
WTA
CCQP
SMO
KKT
OVA
AVA
DT
SVR
RT
KCV
Significato
BackPropagation
Winner Take All
Constrained Convex Quadratic Problem
Sequential Minimal Optimization
Condizioni di Karush–Kuhn–Tucker
One Vs. All
All Vs. All
Decision Trees
Support Vector Regression
Regression Trees
K–Fold Cross Validation
8
Capitolo 1
Introduzione
1.1
Cos’è il Data Mining?
Posto nella Prefazione che in queste dispense ci occuperemo solamente
dei principali algoritmi di Data Mining (DM) per Business Intelligence (BI),
vediamo di approfondire meglio cosa si intende per Data Mining.
Consideriamo il caso di una catena di supermercati e supponiamo di avere
tre centri di vendita: per esempio, Genova, Savona e La Spezia. Ipotizziamo
inoltre di aver sede a Genova e di avere a disposizione un enorme database in
cui salviamo tutte le transazioni (i.e., tutte le vendite) di ogni supermercato.
Da questa montagna di dati vorremmo estrarre, per esempio, informazioni di
più alto livello, come le relazioni fra prodotti venduti. Per renderci conto di
quanti dati potremmo avere a disposizione, basti pensare che, in media, un
supermercato di dimensione medio–grande in una giornata può effettuare più
di 2000 vendite in giorni feriali e 3000 nei festivi. Supponiamo di collezionare
dati per il mese di luglio 2008, che comprende 8 giorni festivi e 23 feriali.
Considerando i 3 supermercati della nostra piccola catena abbiamo:
(2000 · 23 + 3000 · 8) · 3 = 210000,
più di 200000 dati! E solo in un mese!! È abbastanza intuitivo capire che
analizzare ad occhio più di 200mila dati non è banale...
Supponiamo ora di disporre di un algoritmo A in grado di identificare
relazioni fra prodotti venduti: potrebbe sovente capitare che il cliente che
acquista Coca Cola compri anche degli snack. Il nostro algoritmo A individuerà in automatico tali relazioni, che potranno poi essere sfruttate al fine di
9
sistemare Coca Cola e snack in maniera strategica all’interno degli scaffali,
oppure per organizzare le offerte commerciali da proporre ai clienti. Non
solo: si possono utilizzare altri algoritmi B, C,... per individuare altri tipi di
indici o estrarre altre informazioni, dividendo queste ultime sulla base della
città in cui il supermercato è situato o per tipologia di prodotto. Questo
tipo di problema viene detto Market Basket Analysis (MBA) ed è una delle
situazioni in cui le metodologie di BI (e, in particolare, le tecniche di DM)
trovano applicazione.
Altri migliaia di esempi potrebbero essere portati in questa sede. Quello
che ci interessa maggiormente è, ora, cercare di dare una definizione di Data
Mining [9]:
Data mining is the process of selection, exploration, and modelling
of large quantities of data to discover regularities or relations that
are at first unknown with the aim of obtaining clear and useful
results for the owner of the database.
Le metodologie utilizzate dal DM provengono da due mondi diversi, in
generale:
1. alcuni algoritmi sono stati sviluppati nell’ambito del Machine Learning (ML), il cui scopo è di cercare di rappresentare nel miglior modo
possibile il processo di generazione dei dati, in modo tale da evitare
la mera memorizzazione dei dati in favore di un più efficace processo di generalizzazione del modello anche a casi non ancora osservati.
Il primo esempio di algoritmo di ML è stato il percettrone di Rosenblatt [21], dal quale hanno avuto origine modelli sempre più complessi
come i MultiLayer Perceptrons (MLP ), facenti parte della categoria
delle reti neurali (Neural Networks, NN ), di cui torneremo a parlare
a tempo debito. Negli ultimi dieci anni circa, ha preso sempre più
piede, nel campo del ML, l’algoritmo Support Vector Machine (SVM ),
che, basandosi su una teoria statistica molto solida e chiamata Statistical Learning Theory (SLT ) [23], costituisce l’attuale stato dell’arte
nel campo del Machine Learning, almeno per quanto riguarda l’ambito
della classificazione;
2. altri metodi sono stati invece sviluppati nell’ambito delle cosiddette
statistica multivariata e statistica computazionale: è il caso, per esem10
pio, di algoritmi basati sulle teorie di Bayes, come il Naive Bayesian
Classifier (NBC ) [12].
Volendo unire assieme nel mondo del DM i principi della statistica e del
ML, possiamo dire che negli algoritmi di DM devono permettere un’analisi
approfondita dei dati (come i modelli statistici), ma devono anche garantire una sorta di non–memorizzazione del dato (la generalizzazione del ML).
Nelle analisi degli algoritmi di DM, si parte dal principio che ogni dato sia
in qualche modo affetto da rumore: tornando all’esempio del supermercato,
il rumore consiste nel fatto che ognuno di noi ha gusti diversi. Ad esempio,
qualcuno potrebbe gradire acquistare Coca Cola abbinata a salatini, mentre qualcun altro abbina l’acquisto della Coca Cola ad una torta dolce. Se
noi memorizzassimo ogni possibile associazione, senza cercare di estrarre informazione, non avremmo più Data Mining, per la precisione non avremmo
più il Mining! Si viene, quindi, a porre un trade–off tra memorizzazione e
capacità di generalizzazione dei dati disponibili: in pratica, non dovremo avere nè un modello troppo complicato (ovvero, che memorizza perfettamente
sia il dato disponibile sia il rumore che affligge per definizione i dati a nostra disposizione), nè troppo generale, ovvero non più in grado di descrivere
adeguatamente la sorgente dei nostri dati.
Come ogni algoritmo, anche i metodi di DM generano un output, che
sarà di natura diversa a seconda del tipo di applicazione che ci troviamo ad
analizzare (rimandiamo di qualche paragrafo ulteriori chiarimenti a riguardo). Spesso, l’output del nostro modello, nell’ambito della BI, può fornire
nuova ispirazione per raccogliere altri dati, oppure per generare nuovi indici
o ipercubi per l’analisi: ecco perchè, in applicazioni di tipo business, si parla
di circolo virtuoso della conoscenza [5], in quanto l’estrazione di conoscenza
porta a nuove informazioni, che possono a loro volta essere usate per ottenere
ulteriori e più approfondite nozioni a riguardo. Per questi motivi, il DM non
è semplicemente l’utilizzo di uno o più algoritmi o tecniche statistiche su dati
utilizzando un calcolatore; il DM è un processo di BI che dev’essere usato
insieme a tutti gli strumenti di Information Technology (IT ) al fine di fornire
un supporto alle decisioni in ambito aziendale. Non solo: tale informazione
dev’essere utile, quanto più corretta possibile e di facile interpretazione per
tutti, dal consigliere di amministrazione all’impiegato dell’area logistica.
11
Temperatura
32
35
44
28
27
31
Pressione
111
110
144
109
108
110
Guasto
0
0
1
0
0
0
Tabella 1.1: Esempio di controllo sul funzionamento di un macchinario.
1.2
Terminologia di base
Prima di avventurarci in maggiori dettagli, elenchiamo un po’ di termini
di base.
Viene definito dataset un insieme di dati a disposizione per l’analisi: può
essere un data warehouse, un data mart o parte di essi. In particolare, il
dataset utilizzato per creare un modello viene detto training set, in quanto
utilizzato nella fase di training, ovvero di creazione del modello stesso. Quest’ultimo, cosı̀ trovato, verrà quindi usato nella cosiddetta fase in avanti o
feedforward, ovvero lo step di applicazione a run–time. Distingueremo più
avanti in questa dispensa, invece, i validation set e test set.
Un dataset è composto, come dice il nome stesso, di dati: ogni osservazione viene chiamata pattern. Ogni pattern è caratterizzato da un insieme
di valori, detti variabili (variables), attributi (attributes) o features. Ad ogni
pattern può essere assegnato un target, ovvero un valore indicante una particolare proprietà di ogni pattern. In pratica, una feature svolge il ruolo di
target, se cosı̀ deciso da noi. Un paio di esempi chiariranno il tutto.
Consideriamo il dataset di Tab. 1.1: ogni riga del dataset è un pattern,
mentre ogni colonna rappresenta una feature. Questo dataset, in particolare,
è composto da 6 pattern, ognuno dei quali è costituito da 3 variabili (feature).
Possiamo, però, considerare il seguente problma da analizzare: a seconda del
livello di temperatura e pressione, vogliamo controllare se un macchinario è
guasto o funzionante. In tal caso, Guasto svolge il ruolo di target, quindi il
nostro dataset è composto da 6 pattern, 2 attributi e un target.
Nel caso del dataset di Tab. 1.2, invece, abbiamo 6 pattern e 5 feature: in
questo caso, tuttavia, è difficile identificare una feature come target. Difficile
12
Vendita Coca Cola Snack
110500
0
1
110501
1
1
110502
1
1
110503
1
1
0
1
110504
110505
0
1
Pane
0
0
0
0
0
0
Gelato
1
0
0
0
1
1
Tabella 1.2: Esempio di vendite in un supermercato.
ma non impossibile: per esempio, potremmo voler prevedere se un cliente
acquisterà o meno gelato sulla base degli acquisti di Coca Cola, snack e
pane, per quanto analisi di questo tipo non siano particolarmente utili. In
generale, è l’applicazione e il tipo di analisi che ci guidano a selezionare
(eventualmente) una feature come target.
Esistono, peraltro, target di diverso tipo (ove presenti), a seconda del
problema che si vuole affrontare. Normalmente, si usa la seguente notazione
per indicare un dataset dotato di target: {(x1 , y1 ), ...., (xl , yl )}, con xi ∈ m
indicanti i pattern. Quindi, m è il numero di feature, l è il numero di pattern,
mentre yi varia, come detto, a seconda del tipo di problema:
• se yi ∈ {−1, 1} oppure yi ∈ {0, 1}, si parla di classificazione biclasse:
considerando Guasto come target, il dataset di Tab. 1.1 è un esempio
di dataset per classificazione binaria, in cui le feature Temperatura e
Pressione sono utilizzate per cercare una relazione fra esse e, appunto,
Guasto. Tale target può assumere solo due valori binari, in quanto una
macchina può solo essere guasta o funzionante (anche se vedremo che
si può introdurre un discorso di tipo probabilistico, ma ne riparleremo
a tempo debito);
• se yi ∈ S ⊂ ℵ, ovvero il target può assumere solo un certo set di
valori interi, si parla di classificazione multiclasse, semplice estensione
di quanto descritto al punto precedente;
• se yi ∈ si parla di regressione, ed equivale di fatto a trovare una
relazione f (·) del tipo y = f (x).
13
1.3
Data Mining Process
Viene definita Data Mining Process una serie di operazioni che vanno
dalla definizione preliminare degli obiettivi per l’analisi fino alla valutazione
dei risultati ottenuti. Di seguito, elenchiamo le varie attività caratterizzanti
il DM Process, quindi, nei successivi paragrafi, daremo maggiori dettagli sulle
varie fasi di progetto:
1. Definizione degli obiettivi per l’analisi;
2. Selezione, organizzazione ed eventuale preprocessing dei dati;
3. Analisi esplorativa dei dati ed eventuale trasformazione di questi;
4. Scelta delle metodologie di analisi da usare (e comparare);
5. Analisi dei dati, sulla base dei metodi scelti al passo precedente;
6. Comparazione e valutazione delle prestazioni dei diversi metodi; scelta
della metodologia di analisi da utilizzare a run–time;
7. Implementazione del modello scelto, interpretazione dei risultati che
esso fornisce ed utilizzo di questi ultimi nel processo decisionale aziendale.
1.3.1
Definizione degli obiettivi
Sebbene questa fase sembri la più immediata e semplice, non è sempre
cosı̀: spesso gli obiettivi e le problematiche aziendali non sono cosı̀ chiari, nè
è chiaro quali dati, coefficienti o tipologie di analisi debbano essere applicate.
Di sicuro, la grande massa di dati a disposizione non aiuta in questo step:
torniamo al caso della catena di supermercati, ad esempio. Supponiamo
che l’obiettivo prefissato sia di voler aumentare i profitti: che tipo di analisi
vogliamo effettuare sui dati? Trovare le associazioni fra prodotti per organizzare meglio la disposizione degli scaffali o le offerte? Trovare l’andamento
dei guadagni per prodotto e/o supermercato per, eventualmente, decidere di
ingrandire un market o un reparto, o aprirne direttamente uno nuovo?
Questa fase è di certo la più critica, e spesso viene sottovalutata: è
importante che gli obiettivi dell’analisi siano definiti precisamente a priori e
non persistano dubbi prima di passare alle fasi successive.
14
1.3.2
Organizzazione dei dati
Una volta terminata la fase 1.3.1, iniziamo a considerare i dati a nostra
disposizione. Normalmente, in un’azienda si ha a disposizione un grande
database di dati, il data warehouse, da cui estraiamo i data marts.
La prima fase consiste in una preliminare pulizia del dataset, detta data
cleansing: si analizzano tutte le variabili che caratterizzano i dati alla ricerca
di possibili valori mancanti (missing), palesemente sbagliati (incorrect) o
inutili (per esempio, considerando il dataset di Tab. 1.2, il codice della
vendita in molti casi non ha utilità alcuna per un’analisi sui dati). Questa
fase aiuta anche, in maniera retroattiva, a migliorare (se necessario) la qualità
della sorgente dati. Inoltre, il data cleansing permette di effettuare anche una
scelta tra variabili utili e inutili al fine dell’analisi (per esempio, eliminando
feature con molti valori missing).
La seconda fase consiste nella creazione di subset di dati: questo step è
necessario soprattutto quando ci troviamo a trattare masse davvero imponenti di dati, per le quali l’utilizzo di tutto il data mart spesso porta ad avere
meno informazione (meglio, un’informazione meno “pulita”) rispetto all’utilizzo di sottoinsiemi di esso opportunamente scelti. In generale, l’utilizzo di
dataset troppo grandi può portare al fenomeno dell’overfitting, ovvero alla
memorizzazione dei dati (e della realizzazione particolare del rumore che li
affligge). Inoltre, vedremo più avanti nella nostra trattazione come i dati non
selezionati possano diventare ottimo banco di prova per verificare le prestazioni del modello durante la fase 1.3.6. La selezione dei subset, tuttavia, è
tutt’altro che banale, ed è stata affrontata spesso in letteratura [4, 3].
1.3.3
Analisi esplorativa dei dati
Un’analisi esplorativa dei dati è spesso determinante al fine di incrementare la qualità dei risultati ottenuti. Queste metodologie di analisi, simili
nella loro filosofia alle tecniche OLAP (OnLine Analytical Processing), permettono di comprendere meglio l’origine dei nostri dati e trovare relazioni di
base che possono risultare di cruciale importanza per il modello operativo.
L’analisi dei dati passa anche attraverso una selezione dei dati stessi e, in
particolare, si parla di:
• feature selection (altresı̀ variable selection);
15
• feature analysis (altresı̀ variable analysis);
• outlier detection.
La feature selection consta nella selezione di un sottoinsiemi di variabili, caratterizzanti ogni dato, che permettono di preparare e riorganizzare il
nostro data mart (ad esempio) in modo da rendere più semplice e più performante le analisi dei passi successivi. Un esempio dovrebbe chiarire meglio
questo concetto.
Torniamo al caso della catena di supermercati, e supponiamo che il nostro
data mart sia piuttosto piccolo e sia rappresentato in Tab. 1.2: ovviamente,
non è un caso reale, ma ci serve come spunto per qualche riflessione. La
prima colonna rappresenta il codice univoco di una vendita, per esempio il
numero seriale dello scontrino fiscale; le colonne successive rappresentano
4 prodotti che possono essere acquistati: uno 0 indica che quel prodotto
non è stato venduto in quella particolare transazione, mentre un 1 indica
la vendita del prodotto. Notiamo subito due cose: in questo caso, tutti
hanno acquistato snack, e nessuno ha acquistato pane. Pertanto, sia gli
snack sia il pane ci danno informazioni di base (ovvero che ai nostri clienti
piacciono moltissimo i nostri snack e che dobbiamo cambiare panettiere...)
ma sono variabili che potrebbero essere inutili per analisi più sofisticate, non
permettendo distinzioni tra le varie vendite. Come accorgersi di tutto ciò in
casi reali con migliaia di vendite e prodotti? Semplice, basta controllare le
colonne a varianza nulla, ad esempio, o utilizzare appositi algoritmi di ranking
per classificare l’informatività delle variabili (ne parleremo più avanti).
Selezionare un sottoinsieme di variabili può essere utile in quanto:
• spesso feature poco informative peggiorano le prestazioni di un modello;
• molti algoritmi soffrono la curse of dimensionality in rapporto al numero di feature.
Non è sempre vantaggioso, comunque, ridurre il numero di variabili, in
quanto tutto dipende dal tipo di analisi che vogliamo affrontare. Tornando
alla Tab. 1.2, eliminare la colonna snack, in quanto poco informativa, potrebbe essere una buona scelta in alcune metodologie, ma potrebbe, ad esempio,
farci perdere delle relazioni importanti nel caso di cui abbiamo discusso nel
paragrafo 1.1. Morale della favola: la feature selection va applicata con molta
16
3
2.5
2
1.5
1
0.5
0
0
0.2
0.4
0.6
0.8
1
Figura 1.1: Campioni del segnale ignoto y = f (x). In 0.8, si noti il presunto
outlier.
attenzione e solo sapendo esattamente ciò che si sta facendo e l’analisi che
vorremo applicare in seguito.
La feature analysis, invece, consiste nell’analizzare le caratteristiche statistiche di base del nostro insieme di dati e notificare (se è il caso) l’eventuale
mancanza di ulteriori variabili, che potrebbero facilitare le operazioni successive. Di fatto, la feature analysis permette di capire preventivamente
se è meglio intervenire sulla sorgente dati o se le variabili che abbiamo a
disposizione dovrebbero essere sufficienti per gli algoritmi da applicare.
Per spiegare più in dettaglio l’operazione di outlier detection, invece,
dobbiamo definire innanzitutto cos’è un outlier. Un dato viene detto outlier
se è palesemente afflitto da un picco di rumore, quindi se è estremamente
sbagliato. Supponiamo di voler ricostruire una relazione del tipo y = f (x) in
un intervallo [0, 1] a partire da alcuni valori campionati (xc , yc ) e di trovare dei
sample come in Fig. 1.1. Con ogni probabilità, il campione in 0.8 è sbagliato,
magari perchè in quel momento sul sistema è intervenuto un picco di disturbo.
Nella ricostruzione del segnale, mantenere o eliminare l’outlier può avere
influenze importanti sulla qualità del risultato finale: le Figg. 1.2 e 1.3
mostrano due approssimazioni del segnale includendo e escludendo l’outlier.
Abbiamo detto che un outlier è un dato estremamente sbagliato: ma
estremamente, di preciso, cosa significa? Ovviamente, il tutto varia da caso
17
3
2.5
2
1.5
1
0.5
0
−0.5
0
0.2
0.4
0.6
0.8
1
Figura 1.2: Approssimazione escludendo l’outlier.
3
2.5
2
1.5
1
0.5
0
−0.5
0
0.2
0.4
0.6
0.8
1
Figura 1.3: Approssimazione includendo l’outlier.
18
a caso, e molto si basa sulle eventuali informazioni a priori che potremmo
avere a disposizione. Nel caso di Fig. 1.1, qualora sapessimo che i dati
hanno un andamento lineare, ovviamente l’outlier deve essere escluso; senza
informazioni a priori, corriamo comunque un rischio.
Una nota conclusiva: spesso, proprio per i motivi precedentemente presentati, l’outlier detection è considerata, a tutti gli effetti, un metodo statistico da valutare attentamente sulla base della qualità dei risultati ottenuti
e viene pertanto spostata dalla fase di analisi esplorativa dei dati alle fasi
successive del DM Process.
1.3.4
Scelta delle metodologie di analisi
Ci sono moltissimi metodi statistici e ognuno di essi è stato implementato
in una miriade di algoritmi: è importante, quindi, una classificazione di tali
metodi, al fine di fare un po’ di ordine. La scelta del metodo dipende dal tipo
di analisi che vogliamo fare, che a sua volta dipende dagli obiettivi prefissati
e dai dati che abbiamo a disposizione. Per questo motivo, si dice che il Data
Mining Process è guidato dall’applicazione.
Le principali classi di metodi statistici sono:
1. Metodi descrittivi;
2. Metodi predittivi;
3. Metodi locali.
Nei prossimi paragrafi, li presentiamo brevemente.
Metodi descrittivi
Anche detti metodi non supervisionati (unsupervised ) o indiretti, mirano a raggruppare i dati sulla base di relazioni non note (e potremmo dire
“non notabili”) a priori o con un’analisi esplorativa. Nel dataset, non è presente il target. Tra i vari problemi affrontati con metodi descrittivi, noi ci
occuperemo principalmente del clustering.
19
Metodi predittivi
Anche detti metodi supervisionati (supervised ) o diretti, hanno come
obiettivo trovare relazioni tra feature e target, al fine di identificare relazioni
di classificazione o predizione. Nel dataset utilizzato è sempre presente un
target. È il caso dei problemi di classificazione biclasse e multiclasse e della
regressione.
Metodi locali
Hanno come obiettivo identificare particolari caratteristiche e relazioni su
sottoinsiemi del dataset. Esempi sono le association rules, che abbiamo citato
indirettamente nel nostro esempio introduttivo nel paragrafo 1.1. Non solo:
come anticipato in precedenza, anche il problema della outlier detection può
essere considerato un metodo locale e, come tale, potrà poi essere sottoposto
ad attenta valutazione negli step successivi del DM Process.
1.3.5
Analisi dei dati
A questo punto, scelto il metodo (o i metodi) con cui vogliamo affrontare
l’analisi dei dati, scelti gli algoritmi e scelti gli obiettivi, non ci rimane che
dare inizio alle operazioni. In questa fase, potrebbero essere usati software
ad hoc, ma, più in generale, ci si affida ad applicazioni già sviluppate (e testate) disponibili in commercio o per il libero download. Daremo brevemente
un’occhiata a questi software nel paragrafo 1.4, concentrandoci in particolar
modo sul software che useremo: il freeware WEKA.
1.3.6
Valutazione dei metodi statistici e dei risultati
ottenuti
Terminata l’analisi con tutti i metodi prescelti, non ci resta che definire
(se non l’abbiamo già fatto in precedenza) dei coefficienti per la comparazione. Per esempio, nel caso di classificazione, un buon termine di paragone
potrebbe essere l’errore previsto a run–time per ogni metodo e algoritmo, al
fine di scegliere quello che sbaglierà meno. Per trovare questi (o altri) coefficienti, e affinchè essi siano affidabili, è necessario, di norma, affidarsi a metodi
di tipo statistico: analizzeremo più avanti in queste dispense alcune di queste
20
tecniche, come la Cross Validation. Tali tecniche ci devono permettere una
valutazione rapida, semplice e affidabile.
Spesso un coefficiente per la comparazione non è sufficiente, ma è necessario considerare altri fattori quali vincoli temporali o di risorse, qualità e
stabilità del risultato ottenuto, e molto altro ancora.
1.3.7
Implementazione dell’algoritmo
Concludiamo questa carrellata sul DM Process con la fase di realizzazione
del modello: una volta scelto, esso dovrà essere implementato a tutti gli effetti
per entrare in funzione (la già citata fase feedforward) nel nostro business
aziendale. Anche in questo caso, ci si può affidare ad eseguibili in commercio
o freeware. Data l’usuale semplicità di implementazione della fase in avanti di
molti algoritmi, si possono realizzare codici e programmi ad hoc, ottimizzati
e customizzati sulle esigenze aziendali e di analisi.
1.4
Il software che useremo: WEKA
Negli ultimi anni è cresciuto in modo esponenziale il numero di software
per BI che comprendono al loro interno suite per il DM: basti citare Oracle
e Microsoft SQL Server. Date le caratteristiche di prodotti commerciali a
prezzi tutt’altro che contenuti e data l’oggettiva difficoltà di apprendimento
in strumenti più professionali che divulgativi, si è deciso di utilizzare un
programma freeware chiamato Waikato Enviroment for Knowledge Analysis,
in breve WEKA. Esso è stato sviluppato in Nuova Zelanda presso l’Università
di Waikato ed è scaricabile gratuitamente1 . Al proprio interno, comprende
moltissime routine per training e fase in avanti di moltissimi algoritmi.
WEKA è realizzato in Java, pertanto necessita solo della Java Virtual
Machine (JVM) installata sulla propria macchina (è possibile scaricare la
JVM assieme a WEKA in un unico pacchetto dal sito neozelandese). Nel
caso di utilizzo su macchine Windows (qualsiasi versione, Vista incluso), è
possibile installare il programma, che viene compilato con opzioni di compilazione standard. Su altri sistemi operativi (Mac piuttosto che Linux) è
obbligatorio (su Windows è solo opzionale) scaricare i sorgenti e compilarli
prima di eseguire WEKA. La riga di compilazione è la seguente:
1
http://www.cs.waikato.ac.nz/ml/weka/
21
Figura 1.4: Interfaccia di base di WEKA.
java -jar weka.jar
e sarà la JVM a occuparsi del resto. Ulteriori opzioni di compilazione sono
possibili per aumentare la dimensione dello stack o simili.
In Fig. 1.4 viene mostrata l’interfaccia di base di WEKA. Quattro opzioni
sono possibili:
• Simple CLI apre una finestra a riga di comando per qualsiasi tipo di
operazione e analisi sui dati. Essendo poco “user–friendly”, è facilmente
utilizzabile solo da utenti esperti e dopo un po’ di pratica;
• Explorer lancia una finestra GUI per ogni tipo di analisi e operazione sui dati. Explorer è decisamente più intuitivo rispetto alla CLI,
quindi, almeno nei primi tempi, ci dedicheremo soprattutto a questa
applicazione;
• Experimenter permette di confrontare fra loro più metodi di analisi,
comparandone le prestazioni. Il setup di Experimenter non è banale
e necessita di un po’ di esperienza, ma i risultati sono decisamente
interessanti;
22
• Knowledge Flow assomiglia all’ambiente Simulink di MATLAB e consente di costruire confronti fra metodi (tipo Experimenter) ma sotto
forma di diagrammi a blocchi, quindi in modo più intuitivo.
Si noti che WEKA non comprende direttamente al proprio interno un
software per la fase in avanti degli algoritmi: abbiamo anticipato nel paragrafo 1.3.7 come spesso si preferiscano realizzazioni ad hoc, quindi gli autori
di WEKA si sono concentrati sui passi 1–6 del DM Process piuttosto che sul
7. Ciononostante, mostreremo come Explorer e KF possano essere utilizzati
anche per implementare la fase in avanti degli algoritmi.
Dedichiamo qualche cenno al formato dei file in input a WEKA. I dataset
possono essere passati al software in tre differenti modi:
• file ARFF (che analizzeremo a breve);
• indirizzo web (per database di tipo Java DB);
• file locale Java DB.
Premesso che probabilmente nel corso dell’insegnamento utilizzeremo
esclusivamente i file locali ARFF, analizziamone la struttura (può essere utile
per scrivere eventuali convertitori da altri formati per dataset). Ogni riga
preceduta dal carattere jolly ‘%’ è considerata un commento, mentre sono
necessari i seguenti campi:
• un campo @relation, seguito dal nome del dataset;
• l’elenco degli attributi, uno per riga, aventi la seguente struttura:
– la parola chiave @attribute;
– il nome dell’attributo;
– il set di valori che la variabile può assumere (per attributi di tipo
qualitativo o quantitativo discreto) o, in alternativa, il tipo di
feature (real o integer);
• la parola chiave @data, seguita nella linea successiva da tutti i pattern.
Ogni pattern è costituito dalle feature, divise dal carattere ‘,’. Un
missing è contraddistinto da ‘?’.
23
1.5
Organizzazione della dispensa
Questa dispensa è organizzata sulla base del flusso del Data Mining Process, di cui analizzeremo (per motivi di tempo) solamente alcuni aspetti. In
particolare:
• nel Capitolo 2, affronteremo il problema dell’organizzazione dei dati,
delle trasformazioni applicabili ai pattern e dei tipi di variabili;
• nel Capitolo 3, approfondiremo alcuni concetti su parametri statistici
e caratteristiche del nostro dataset;
• nel Capitolo 4, invece, cominceremo ad analizzare alcuni algoritmi per
la classificazione di pattern;
• nel Capitolo 5 affronteremo il problema della regressione;
• il clustering sarà, invece, l’argomento centrale del Capitolo 6;
• trovare le regole di associazione tra feature di un dataset è il problema
affrontato nel Capitolo 7;
• termineremo presentando alcuni metodi pratici per il confronto fra algoritmi e introducendo l’utilizzo di WEKA Knowledge Flow nel Capitolo
8.
24
Capitolo 2
Organizzazione dei dati
In questo capitolo andiamo ad affrontare brevemente le problematiche
relative all’organizzazione dei dati. Dati per scontati concetti quali data
warehouse e data marts, partiamo dal presupposto di avere a disposizione
un dataset, composto da l pattern e m feature, come definito nel paragrafo
1.2. Al momento, non ci interessa se il dataset è dotato di target o meno.
Tralasciamo per il momento, inoltre, la selezione di un subset adatto: è un
problema decisamente complesso, che richiameremo solo in parte a tempo
debito, negli ultimi capitoli di queste dispense.
Per quanto riguarda le prime applicazioni usando WEKA, rimandiamo alla fine del prossimo capitolo, quando avremo terminato questa breve
carrellata sull’analisi e l’organizzazione dei dati.
2.1
Tipi di attributi
Le feature possono essere organizzate in due principali categorie, a loro
volta divise in due sottocategorie:
1. Variabili qualitative:
(a) nominali;
(b) ordinali;
2. Variabili quantitative:
(a) discrete;
25
(b) continue.
Nei prossimi paragrafi dettagliamo i tipi di attributi precedentemente
elencati.
2.1.1
Variabili qualitative
Le feature di tipo qualitativo sono di solito legate ad aggettivi riferiti ad
un particolare attributo e possono essere classificate in livelli, detti categorie.
Esempi sono il codice postale o il sesso di una persona.
Variabili qualitative nominali
Una variabile qualitativa è detta nominale se è organizzata su diverse
categorie, per le quali non è possibile definire un ordine preciso. In particolare, è possibile definire rapporti di uguaglianza e disuguaglianza (= e =)
tra diversi livelli. Esempio sono le codifiche per il sesso: è possibile definire
rapporti di uguaglianza (ad esempio, M = M), ma non un ordine fra sessi
(non si può definire un rapporto M < F , ad esempio).
Variabili qualitative ordinali
Viceversa, sono dette ordinali le variabili qualitative per le quali è possibile stabilire un ordine (operazioni <, >, =), ma senza la possibilità di quantificare la differenza fra livelli. Un esempio è una classifica di una gara podistica: se noi non indichiamo i distacchi, ma solo le posizioni finali, da esse si
può stabilire l’ordine d’arrivo ma non quantificare la distanza fra un atleta e
l’altro.
2.1.2
Variabili quantitative
Le feature quantitative sono strettamente legate alle quantità numeriche
che le descrivono ed è possibile non solo stabilire un ordine (operazioni <, >
, =), ma anche quantificare la distanza (in senso generico) fra vari livelli. È
il caso dell’età di una persona, ad esempio: è possibile non solo dire che una
persona di 20 anni è più giovane di una di 45, ma anche che ci sono 25 anni
di differenza fra i due.
26
Variabili quantitative discrete
Una variabile quantitativa è discreta solo se può assumere un numero
finito di valori. È il caso di segnali campionati, per esempio. Si distingue dalle
variabili qualitative nominali perchè è possibile definire quantitativamente la
distanza fra i livelli.
Variabili quantitative continue
Una variabile quantitativa è continua se può assumere un numero infinito
di valori. Per esempio, una temperatura registrata da un sensore ad alta
precisione può essere considerata a tutti gli effetti una variabile quantitativa
continua. A tutti gli effetti, ricordiamo comunque che variabili continue su
un calcolatore non possono nè potranno mai esistere, sebbene 32 (o 64) bit
di precisione siano più che sufficienti per approssimare ogni variabile discreta
come continua.
2.2
La matrice dei dati
Abbiamo anticipato nel paragrafo 1.2 la rappresentazione di una matrice
dati, notazione che ripetiamo per comodità:
{x1 , ...., xl } ,
(2.1)
e rappresentante un dataset composto da l pattern (in questo caso, supponiamo non sia presente target). Abbiamo inoltre stabilito che ogni pattern
xi ∈ m , ovvero abbiamo m feature. Viene chiamata matrice dei dati (data
matrix ) la rappresentazione matriciale di tale dataset:
⎡
x1,1 · · · x1,j · · · x1,m
⎢ .
..
..
..
..
⎢ ..
.
.
.
.
⎢
⎢
X = ⎢ xi,1 · · · xi,j · · · xi,m
⎢ .
..
..
..
..
⎢ ..
.
.
.
.
⎣
xl,1 · · · xl,j · · · xl,m
⎤
⎥
⎥
⎥
⎥
⎥.
⎥
⎥
⎦
(2.2)
Quindi, l’elemento ij–esimo xi,j rappresenta la j–esima feature dell’i–
esimo pattern della matrice. D’ora in poi, questa notazione verrà utilizzata
27
implicitamente, anche quando non ci riferiremo espressamente alla matrice
dei dati X.
2.2.1
Gestione delle variabili
Come detto, i nostri dati possono essere rappresentati utilizzando una
matrice o, in alternativa, una rappresentazione ad insiemi. Le variabili xi,j
devono essere, quindi, quantità numeriche. Inoltre, in molti algoritmi la
distanza tra pattern svolge un ruolo centrale nella scelta del modello ottimo.
Se, di solito, non ci sono problemi per quanto riguarda le variabili quantitative
(in quanto rappresentate già da valori numerici), possono sorgere difficoltà
per le feature qualitative.
Siano attributi qualitativi nominali o ordinali, spesso essi vengono salvati
nel data warehouse (in generale) sotto forma “testuale”. La trasformazione
in variabili numeriche avviene attraverso la cosiddetta binarizzazione, ovvero l’assegnazione di un codice binario per ognuno dei valori assunti dalla
feature. Supponiamo che una variabile sia di tipo qualitativo e possa assumere r distinti livelli. Verranno create, quindi, r nuove variabili quantitative
binarie in codice one hot, ovvero la variabile binaria equivarrà a 1 solo se
corrispondente all’originale livello della variabile qualitativa.
Un esempio dovrebbe chiarire il tutto. Supponiamo di considerare una
variabile qualitativa v che può assumere 3 distinti livelli: a, b oppure c.
Codifichiamo i 3 livelli utilizzando un codice binario one hot, come quello
rappresentato in Tab. 2.1. Supponendo di avere una matrice di dati X
come in Eq. (2.3), caratterizzata da 5 pattern e 2 feature, attraverso la
binarizzazione otteniamo la matrice dei dati finale Xf di Eq. (2.4), avente
sempre 5 pattern, ma 4 attributi:
⎡
⎢
⎢
⎢
X =⎢
⎢
⎢
⎣
1.1
3.5
1.4
9.0
3.1
28
a
b
b
c
a
⎤
⎥
⎥
⎥
⎥.
⎥
⎥
⎦
(2.3)
Variabile qualitativa
v
a
b
c
Codifica
v1 v2 v3
1 0 0
0 1 0
0 0 1
Tabella 2.1: Esempio di codifica per variabile qualitativa.
⎡
⎢
⎢
⎢
Xf = ⎢
⎢
⎢
⎣
1.1
3.5
1.4
9.0
3.1
1
0
0
0
1
0
1
1
0
0
0
0
0
1
0
⎤
⎥
⎥
⎥
⎥.
⎥
⎥
⎦
(2.4)
La binarizzazione è estremamente utile in molti casi, ma comporta un
aumento del numero di feature: abbiamo già discusso nel paragrafo 1.3.3
che questa non è sempre una scelta ottimale. Un analisi preliminare serve
anche per cercare una codifica efficace e/o per eliminare, ove consentito, il
salvataggio di variabili di tipo qualitativo in memoria (agendo sulla sorgente
di osservazioni).
2.3
Normalizzazione di un dataset
La normalizzazione di valori è una delle operazioni che più di frequente
vengono effettuate su un dataset per svariati motivi. Numerici, innanzitutto,
in quanto eventuali valori nell’ordine di 103 o superiori possono portare a
problemi di overflow (e viceversa, ovvero valori sotto 10−3 possono portare
all’underflow).
Esistono diverse tecniche per la normalizzazione: le più comuni prevedono di riportare i dati della nostra matrice X all’interno dell’intervallo [0, 1]
o [−1, 1]. Dovrebbe ora risultare più chiaro come mai si sia tanto insistito
su data cleansing e analisi dei dati nel capitolo 1. Supponiamo di avere una
matrice di dati
29
⎡
⎢
⎢
⎢
X=⎢
⎢
⎢
⎣
1.1
3.5
1.4
9.0
3.1
4.1
6.5
108
1.9
5.0
⎤
⎥
⎥
⎥
⎥:
⎥
⎥
⎦
(2.5)
con ogni probabilità, x3,2 = 108 rappresenta un errore di misura. Se non ce
ne accorgessimo, potremmo semplicemente normalizzare la nostra matrice fra
[0, 1] e ottenere una matrice con elementi < 10−7 , ad eccezione di x3,2 = 1.
30
Capitolo 3
Analisi esplorativa dei dati
In questo capitolo, affronteremo brevemente il problema dell’analisi esplorativa dei dati, presentando alcuni indici statistici. Questo capitolo potenzialmente potrebbe coprire un intero insegnamento, quindi ci limiteremo a
qualche nozione di base, anche in relazione agli strumenti operativi forniti da
WEKA. Per maggiori dettagli, gli interessati possono fare riferimento a [10].
3.1
3.1.1
Distribuzioni di frequenza
Distribuzioni univariate
A volte è utile analizzare le distribuzioni dei valori che può assumere una
variabile di tipo qualitativo, oppure quantitativa discreta. Questo tipo di
analisi può essere estesa anche alle variabili quantitative continue, cercando gli intervalli ottimi in cui dividere i valori assunti dalle feature (ce ne
occuperemo brevemente quando parleremo di alberi di decisione).
Supponiamo di considerare una variabile v e che essa possa assumere
un numero finito k di livelli, ovvero v = {v1∗ , ..., vk∗ }. Si definisce frequenza
assoluta il numero di occorrenze ni di un livello in un dataset. Ad esempio,
Tab. 3.1 riporta le distribuzioni assolute per la seconda feature della matrice
X dell’Eq. (2.3).
Si definisce frequenza relativa la frequenza assoluta normalizzata per il
numero totale di pattern, ovvero:
pi =
ni
.
l
31
(3.1)
Livello
na
nb
nc
Frequenza
2
2
1
Tabella 3.1: Esempio di frequenza assoluta per una feature qualitativa.
Livello
pa
pb
pc
Frequenza
0.4
0.4
0.2
Tabella 3.2: Esempio di frequenza relativa per una feature qualitativa.
Tab. 3.2 riporta le frequenze relative per il dataset X. Proprietà banali sono
che i ni = l e i pi = 1.
3.1.2
Distribuzioni bivariate e multivariate
Nel precedente paragrafo abbiamo considerato sempre solo una variabile
per volta; ora, invece, siamo interessati ad una statistica “incrociata” delle
variabili. Inoltre, sarebbe possibile estendere il ragionamento a più feature,
ma per brevità ci limiteremo a descrivere le distribuzioni bivariate.
Analogamente a quanto visto nel paragrafo precedente, supponendo di
avere due variabili qualitative v e z, che possono assumere, rispettivamente,
k e h livelli, si definisce frequenza assoluta congiunta nvz (vi∗ , zj∗ ) il numero
di osservazioni in cui, contemporaneamente, la variabile v assume livello vi∗
e la feature z vale zj∗ . Si definisce frequenza relativa congiunta pvz (vi∗ , zj∗ ) la
frequenza assoluta congiunta, normalizzata per il numero totale di pattern l.
È possibile, inoltre, trovare una matrice, detta matrice di contingenza
C ∈ k×h , che comprende al proprio interno tutti i valori di frequenze assolute
congiunte. In pratica, l’elemento ij–esimo Cij equivale alla frequenza assoluta
congiunta nvz (vi∗ , zj∗ ).
32
3.2
Analisi esplorativa univariata
Abbiamo visto nel precedente paragrafo come si possano analizzare le
frequenze univariate o bivariate per le occorrenze di variabili qualitative (con
eventuale estensione al caso di feature quantitative). Ora ci occupiamo di
estrarre una descrizione di massima del nostro dataset, sulla base di indici
di posizione, varibilità ed eterogeneità. Prima, però, un breve richiamo sulle
caratteristiche degli stimatori (in poche parole, gli indici che andremo a breve
a presentare), utili per capire alcuni concetti dei prossimi paragrafi.
3.2.1
Richiami su stimatori e loro caratteristiche
Supponiamo di considerare un generico parametro da stimare α e consideriamo un suo stimatore α̂. A titolo di esempio, si potrebbe considerare
come parametro da stimare l’età media di tutta la popolazione mondiale e
come stima l’età media di un campione di N persone. Esistono due quantità
che definiscono la qualità di uno stimatore e sono:
1. la polarizzazione o bias;
2. la stabilità.
Se uno stimatore è non polarizzato (unbiased ) e stabile viene detto consistente. Tutti gli stimatori che presenteremo nei prossimi paragrafi sono consistenti, ad eccezione di uno (la stima della varianza), per il quale presenteremo
la variante biased e consistente.
Bias di uno stimatore
Viene definito bias di uno stimatore la quantità:
b = α − E {α̂ |α} ,
(3.2)
dove
E {α̂ |α} =
+∞
−∞
···
+∞
−∞
α̂ p (x1 , ..., xN |α ) dx1 · · · dxN
(3.3)
è il valor medio condizionale della stima. Uno stimatore è detto unbiased se
vale
33
lim b = 0,
N →+∞
(3.4)
ovvero se, al crescere all’infinito del numero di osservazioni, il valore vero del
parametro e la sua stima tendono a coincidere asintoticamente.
Stabilità di uno stimatore
La stabilità di uno stimatore viene calcolata utilizzando la varianza esatta
dello stimatore (riparleremo nei prossimi paragrafi di varianza, ma in quel
caso faremo riferimento allo stimatore della varianza):
σα̂2 = E α̂2 |α − E {α̂ |α }2 .
(3.5)
Al crescere del numero di osservazioni, ci aspettiamo che il nostro valore
stimato si avvicini in media sempre più al valore da stimare (bias nullo), ma
anche che tale valore medio sia stabile rispetto alle oscillazioni del parametro
reale (varianza nulla). Pertanto, la seconda condizione che poniamo per la
consistenza di uno stimatore è che
lim σα̂2 = 0.
N →+∞
3.2.2
(3.6)
Indici di posizione
Il più comune indice di posizione è la media aritmetica, definita su un set
di N osservazioni come:
N
i=1
xi
(3.7)
N
ed è calcolabile solo nel caso di variabili quantitative. Ovviamente, la media
da sè ha poco significato, in quanto può fortemente risentire di possibili valori
fuori scala. Vedremo come essa vada integrata nell’analisi da altri indici.
Solo nel caso di variabili quantitative discrete (che possono assumere un
numero finito k di valori), avendo a disposizione le distribuzioni di frequenza,
in particolare le frequenze relative pi di cui al paragrafo 3.1.1, la media può
anche essere calcolata come:
x=
x=
k
i=1
34
pi x∗i ,
(3.8)
dove x∗i rappresentano i k livelli che la variabile può assumere.
Un secondo importante indice di posizione è la moda: essa può essere
calcolata sia per variabili qualitative che quantitative (nel caso di variabili
continue, si rende necessaria un’apposita discretizzazione) e corrisponde al
valore (o all’intervallo) della variabile caratterizzata dalla più alta frequenza
assoluta.
Un terzo indice è la mediana: in una sequenza ordinata di dati, la mediana è il punto per il quale metà dati sono maggiori di esso e metà sono
più piccoli. In altre parole, la mediana è il punto per il quale la probabilità
che un valore caschi alla sinistra di esso o alla destra di esso è pari al 50%.
Necessitando di un ordine fra dati, le operazioni <, >, = devono poter essere definite: pertanto, la mediana è calcolabile per le variabili quantitative e
qualitative ordinali.
3.2.3
Indici di variabilità
Altro indice importante è la variabilità, ovvero la dispersione di una
distribuzione. Esistono diverse tecniche per valutare la variabilità, ma tutte
sono solamente applicabili alle variabili quantitative: è necessario, infatti,
non solo essere in grado di definire un ordine tra i valori, ma anche poterne
definire una misura di distanza.
La prima consiste nel considerare il valore minimo e massimo che l’attributo può assumere: è una tecnica piuttosto elementare, ma che risente
enormemente della presenza di eventuali outliers non identificati. Viene,
quindi, poco usata.
La seconda tecnica consiste nel calcolare la varianza: attenzione, nel
paragrafo 3.2.1 abbiamo parlato di varianza di uno stimatore, qui stiamo
parlando di stima della varianza, ovvero cercare di valutare la varianza della
popolazione utilizzando un campione limitato. La varianza viene calcolata
come:
1 (3.9)
(xi − x)2 ,
N
dove x è la media. Spesso, dato che l’Eq. (3.9) rappresenta uno stimatore
della varianza della popolazione, si utilizza s2 invece di σ 2 .
Sfortunatamente, si può facilmente dimostrare che lo stimatore di Eq.
(3.9) è biased. Uno stimatore unbiased è invece il seguente:
σ2 =
35
1 (xi − x)2 .
(3.10)
N −1
In alternativa alla varianza, si può utilizzare la deviazione standard σ,
che è semplicemente la radice quadrata della varianza.
Altro indice è rappresentato dal coefficiente di variazione (CV ), calcolabile quando la media non è nulla:
σ2 =
CV =
σ
.
|x|
(3.11)
In alternativa agli indici di variabilità fin qui presentati, è talvolta utilizzata l’analisi dei quartili : un quartile è ognuno dei tre punti che divide
un dataset in aree al 25% di probabilità. In particolare, il secondo quartile
equivale alla mediana. I tre quartili vengono definiti come Qi , con i = 1, 2, 3.
Un indice di variabilità è dato dall’Inter–Quartile Range (IQR):
IQR = Q3 − Q1 ,
(3.12)
cioè dalla differenza fra il valore del terzo e del primo quartile. È inoltre
possibile calcolare gli upper bound e lower bound del nostro dataset, definiti
come T1 e T2 :
T1 = max(minimo valore osservato, Q1 − 1.5 · IQR)
(3.13)
T2 = min(massimo valore osservato, Q3 + 1.5 · IQR).
(3.14)
A partire dai quartili e dai bound, è possibile tracciare i cosiddetti boxplot, che identificano graficamente le quantità descritte in precedenza. Fig.
3.1 mostra un esempio di boxplot, in cui vengono anche segnalati eventuali
outliers, calcolati semplicemente (ma, spesso, efficacemente) come tutti quei
valori assunti dalla nostra variabile più piccoli (più grandi) di T1 (T2 ).
3.2.4
Indici di eterogeneità
Gli indici fin qui analizzati sono utili quasi esclusivamente in caso di
variabili quantitative. Comunque, risulta utile, in molti casi, avere anche
misure in grado di descrivere feature di tipo qualitativo, siano esse nominali
o ordinali. L’indice più comune per gli attributi qualitativi è l’eterogeneità.
36
Figura 3.1: Esempio di boxplot.
Consideriamo una variabile qualitativa x, che può assumere k distinti
livelli. Supponiamo di aver calcolato le frequenze relative pi per ogni livello,
come mostrato nel paragrafo 3.1.1. Una definizione generale di eterogeneità
può essere la seguente:
• si ha eterogeneità minima (si parla anche, in questo caso, di omogeneità) quando non abbiamo variazioni nei livelli delle feature, ovvero
una certa pi = 1 e vale pj = 0, ∀j = i;
• viceversa, si ha eterogeneità massima quando le osservazioni si distribuiscono uniformemente su tutti i livelli, ovvero pi = 1/k, ∀i.
Esistono due indici molto comuni di eterogeneità. Il primo è il cosiddetto
Gini index :
G=1−
k
p2i ,
(3.15)
i=1
per il quale è facile mostrare come, se siamo in condizioni di omogeneità, si
ha G = 0, mentre in condizioni di massima eterogeneità si ha G = 1 − k1 .
Dato che spesso può essere utile normalizzare i valori degli indici affinchè
siano compresi in [0, 1], si può definire il Gini index normalizzato:
G =
G
.
(k − 1)/k
(3.16)
Altro indice piuttosto comune è l’entropia, definita come:
E=−
k
i=1
37
pi log pi ,
(3.17)
che vale 0 in caso di omogeneità e log k in caso di massima eterogeneità. Anche in questo caso, è possibile definire l’entropia normalizzata nell’intervallo
[0, 1]:
E =
3.3
E
.
log k
(3.18)
Analisi esplorativa bivariata e multivariata
Analogamente a quanto visto in precedenza per le distribuzioni di frequenza, è ovviamente possibile effettuare analisi incrociate sulle caratteristiche dei nostri dati anche dal punto di vista del calcolo di indici. Dato
che questo tipo di analisi è tutt’altro che banale, ne daremo solo alcuni brevi
cenni, rimandando poi gli interessati ad ulteriori approfondimenti su appositi
testi.
Per quanto riguarda l’analisi bivariata, normalmente un buon metodo
per trovare eventuali relazioni fra feature consiste nell’utilizzare l’approccio
grafico. A tal proposito, molto utilizzato è lo strumento della scatterplot
matrix, in cui gli attributi vengono messi in relazione a coppie. Ogni cella
della matrice è detta scatterplot diagram. Un esempio di scatterplot matrix
è riportato in Fig. 3.2.
Analogamente a quanto visto nel precedente paragrafo, sarebbe possibile
definire moltissimi indici anche per l’analisi bivariata: per brevità citiamo,
in questa sede, solo l’indice di concordanza, ovvero la tendenza ad osservare
alti (bassi) valori di un attributo in accordo con alti (bassi) valori di un’altra
feature. In questo senso, la misura più utilizzata è la covarianza, definita
come:
N
1 Cov(x, y) =
(xi − x) (yi − y) .
N i=1
(3.19)
È immediato notare che Cov(x, x) = σ 2 . Ovviamente, analogamente a quanto visto nel paragrafo 3.1.2, è possibile costruire una matrice di varianza–
covarianza, simile alla matrice di contingenza. In alternativa alla covarianza,
è possibile utilizzare la correlazione (lineare):
38
Figura 3.2: Esempio di scatterplot matrix.
r(x, y) =
Cov(x, y)
,
σx σy
(3.20)
dove σx e σy rappresentano le deviazioni standard delle due variabili. La
correlazione lineare ha le seguenti proprietà:
• r(x, y) = 1 quando tutti i punti nello scatterplot diagram sono posizionati su una retta a pendenza positiva, e r(x, y) = −1 quando la
pendenza è negativa. Proprio per questa relazione di tipo lineare, r
viene chiamata correlazione lineare;
39
Feature
outlook
temperature
humidity
windy
play
Descrizione
Tipo
Condizioni del meteo
Qualitativa nominale
Temperatura atmosferica
Quantitativa continua
Umidità atmosferica
Quantitativa continua
Situazione del vento
Qualitativa nominale
(Target) Giocare o meno a golf Qualitativa nominale
Tabella 3.3: Il dataset weather.
• se r(x, y) = 0, le due variabili non sono assolutamente legate da alcuna
relazione lineare, e si dicono scorrelate;
• in generale, −1 ≤ r(x, y) ≤ 1.
Si potrebbero ora approfondire le analisi di tipo multivariato, ma risultano piuttosto complesse, in quanto è forte in questi casi la distinzione fra i
vari tipi di attributo. Quindi, rimandiamo gli interessati ad approfondimenti
su appositi testi.
3.4
Esempi di analisi con WEKA
Analizziamo un dataset piuttosto elementare utilizzando WEKA. In particolare, analizziamo in questo paragrafo il dataset chiamato weather, e riferito ad una collezione di osservazioni riferite al meteo (sereno, nuvoloso o
piovoso), temperatura, umidità e situazione del vento (presente o assente).
La classe è costituita da una variabile binaria riferita alla possibilità o meno
di giocare a golf, sulla base delle condizioni climatiche. Le feature e il target
di questo dataset sono ricapitolati in Tab. 3.3.
Lanciamo quindi WEKA ed avviamo l’explorer. Sull’interfaccia, clicchiamo su “Open file...” e selezioniamo, dalla cartella “Data”, il file “weather.arff”. Dovrebbe apparire una finestra simile a quanto mostrato in Fig.
3.3. Interpretiamo un po’ tutte le informazioni che ci vengono fornite.
In alto troviamo una serie di tasti, i primi per caricare dataset, mentre gli ultimi due servono per editare (sfruttando una GUI) e salvare il nostro dataset (per esempio, per verificare eventuali missing, completare i dati,
correggere valori palesemente sbagliati e via dicendo).
40
Figura 3.3: Esempio dell’interfaccia explorer di WEKA.
Scendendo, troviamo la possibilità di scegliere dei filtri da appicare ai
dati. Cliccando sul pulsante di scelta, si apre una box ricca di filtri, sia
supervisionati (tengono conto del target) che non supervisionati (viceversa).
A loro volta, i metodi sono divisi in metodi che agiscono sugli attributi o
sulle singole istanze. Lasciando poi alla vostra curiosità maggiori dettagli
su molti di questi filtri, da usare sempre e comunque con un obiettivo ben
fissato, supponiamo di scegliere fra gli unsupervised che agiscono sulle singole
osservazioni (istances) il Randomize, e vediamo di cosa si occupa. Una volta
scelto, clicchiamo sul nome del filtro e si apre una finestra come quella di
Fig. 3.4: ci viene fornita una breve spiegazione del filtro (semplicemente,
randomizza l’ordine dei pattern all’interno del dataset, azione utile quando
vengono usate tecniche per la stima delle performance di un metodo nei
casi di dataset ordinati rispetto al target), con la possibilità di saperne di
più (pulsante “More”); quindi, ci vengono proposte le possibili opzioni. In
questo caso, possiamo solo modificare il seed dell’algoritmo di random.
Altro filtro molto usato è la normalizzazione (normalize), che troviamo
tra gli unsupervised sia per attributi che per singole istanze. La differenza
sta nel fatto che il primo normalizza tutta la matrice dati nell’intervallo [0, 1],
mentre il secondo normalizza ogni singolo pattern affinchè la sua norma p sia
41
Figura 3.4: Esempio di box con dettagli per un filtro.
uguale ad un certo valore:
xi p = s, ∀i = 1, .., n,
(3.21)
dove p e il valore desiderato s sono assegnati dall’utente.
Torniamo a WEKA explorer. Ci vengono fornite, di seguito, alcune informazioni sul dataset: nome, numero di pattern e di attributi (target incluso).
Seguono l’elenco degli attributi e la possibilità di rimuoverne uno o più dall’elenco. A destra, troviamo, per l’attributo evidenziato, le caratteristiche di
distribuzione di frequenza o di indici statistici a seconda che si tratti, rispettivamente, di una feature qualitativa o quantitativa. Più in basso, troviamo
la possibilità di scegliere un attributo come classe e, a seguire, l’istogramma
rappresentativo delle distribuzioni viene rappresentato, utilizzando più colori
per rappresentare i pattern afferenti alle diverse classi. Nel caso di variabili
continue, il range viene suddiviso in un numero adeguato di intervalli.
Agendo su queste opzioni grafiche e sui filtri, un’analisi esplorativa di base
dei dati può essere facilmente eseguita. Non solo: agendo sul tab “Visualize”
in alto, viene mostrata la scatterplot matrix, con la possibilità di visualizzare
i singoli scatterplot diagram cliccando sulle celle della matrice: un esempio
è mostrato in Fig. 3.5.
42
Figura 3.5: Esempio di scatterplot matrix e scatterplot diagram.
3.5
Riduzione di dimensionalità
Abbiamo già parlato in fase di introduzione di riduzione di dimensionalità
e dei possibili pro e contro di questo approccio. Premettendo che esistono migliaia di tecniche per selezionare un subset di variabili, noi ci concentreremo
su uno dei più utilizzati: la Principal Component Analysis (PCA) [13, 17].
Vedremo più avanti che non sempre la PCA rappresenta la soluzione ottima
per la feature selection, ma essa rimane una delle tecniche più diffuse.
La PCA consta di alcuni passaggi:
1. calcolo della matrice di covarianza, che definiamo C ∈ m×m , dove m
è il numero di feature;
2. calcolo degli autovettori e autovalori di C e diagonalizzazione di C. Viene trovata una matrice diagonale D ∈ m×m , i cui elementi di,i = λi ,
ovvero sulla diagonale troviamo gli autovalori precedentemente calcolati;
3. gli autovalori e i corrispondenti autovettori vengono ordinati in maniera
decrescente;
43
4. viene calcolata l’energia cumulativa totale di tutti gli autovettori come
g=
m
di,i ;
(3.22)
i=1
5. viene stabilita una soglia percentuale gth sull’energia cumulativa totale
g;
6. vengono mantenuti solo gli mP CA autovettori e autovalori che permettono di ottenere un’energia cumulativa parziale gp ≥ gth .
Tutto ciò cosa significa? La parte più difficile di tutta la PCA è esattamente questa: interpretare i risultati. In pratica, il calcolo degli autovettori implica che noi andiamo ad effettuare nient’altro che una combinazione
lineare delle nostre feature, ottenendo mP CA nuove feature. L’operazione
di sogliatura significa, semplicemente, tagliare quelle componenti che meno
influiscono sulla descrizione dello spazio degli ingressi.
Ovviamente, se il nostro scopo è, in aggiunta alla riduzione della dimensionalità, mantenere anche l’interpretabilità degli attributi, la PCA non è
di certo la via più adatta da seguire. Ciononostante, è possibile effettuare, sfruttando le proprietà della cosiddetta Singular Value Decomposition
(SVD), la trasformazione inversa nell’ambito dello spazio originale degli attributi: il problema, in questo caso, è che non possiamo permetterci di escludere alcun autovettore, quindi non effettuiamo di fatto alcuna riduzione di
dimensionalità!
3.6
Esempi di riduzione di dimensionalità utilizzando WEKA
Proviamo ora ad applicare la PCA in WEKA. Prima di tutto, lanciato
explorer e caricato il dataset weather, spostiamoci sul tab “Select attributes”
e selezioniamo dal menù la PCA (“PrincipalComponents”). Lasciamo intatte
le opzioni di default, utilizziamo il ranker di WEKA (classifica le variabili
usando indici basati sull’entropia) e forziamo WEKA a usare tutto il training
set (lasciamo per ora perdere la Cross Validation, di cui parleremo più avanti
in queste dispense). Selezionata la classe (“play”), lanciamo l’esecuzione
della PCA.
44
L’output di WEKA conterrà, in ordine: un riepilogo del dataset e dei metodi selezionati; la matrice di correlazione (usata in alternativa alla matrice
di covarianza); gli autovalori, la porzione di energia corrispondente, l’energia
cumulativa totale fino a quell’autovalore e il corrispondente autovettore; la
matrice degli autovettori; il ranking delle variabili (in questo caso, le combinazioni lineari calcolate con la PCA), ordinate dal ranker di WEKA. Notiamo
che, avendo una variabile nominale qualitativa (il meteo) che può assumere
3 possibili livelli, WEKA effettua la binarizzazione; la situazione del vento è
anch’essa qualitativa, ma binaria e non necessita di ulteriore binarizzazione.
Alla fine, abbiamo 6 attributi da considerare. Notiamo che compaiono solo 5
autovalori, il che equivale a dire che il sesto autovalore è nullo; questo fatto
è confermato anche dall’energia cumulativa, che raggiunge il 100% con solo i
primi 5 autovalori.
Passiamo ora a capire meglio le opzioni della PCA. Possiamo settare:
• il massimo numero di attributi che vogliamo visualizzare nella combinazione lineare (per semplicità di lettura);
• se vogliamo normalizzare i dati fra [0, 1], qualora non l’avessimo già
fatto;
• un flag per trasformare nuovamente le feature della PCA nello spazio
originario attraverso SVD;
• la percentuale di energia cumulativa che vogliamo garantire.
Analizzando il ranking ottenuto in precedenza:
Ranked attributes:
0.675990846445273472
0.411301353536642624
0.195956514975330624
0.063841150150769192
0.000000000000000111
1
2
3
4
5
0.578temperature...
-0.68outlook=overcast...
0.567outlook=sunny...
0.738windy...
0.748temperature...
notiamo che la quinta componente della PCA ha un ranking davvero basso, e
stesso dicasi per la quarta. Potrebbe essere, quindi, una buona idea abbassare
la soglia per l’energia cumulativa: portiamolo al 90%, ad esempio, valore
piuttosto tipico. Prima di lanciare la simulazione, diamo un’occhiata anche
alle opzioni del ranker:
45
• possiamo scegliere se fare effettuare il ranking o no;
• possiamo settare il numero massimo di feature da mantenere;
• possiamo selezionare un subset iniziale di attributi;
• possiamo stabilire una soglia per il valore dell’entropia sotto la quale
la variabile viene esclusa dal dataset.
Lasciamo le impostazioni di default, e lanciamo la PCA. Come previsto,
otteniamo solo 4 componenti. Possiamo continuare a fare analisi di questo
tipo, ma adesso vogliamo effettuare una verifica: la sesta componente è davvero nulla? Settiamo la soglia di energia al 100%, ovvero includiamo tutto.
In effetti, il sesto autovettore è nullo:
eigenvalue proportion cumulative
1.94405
0.32401
0.32401 0.578temperature...
1.58814
0.26469
0.5887 -0.68outlook=overcast...
1.29207
0.21534
0.80404 0.567outlook=sunny...
0.79269
0.13212
0.93616 0.738windy...
0.38305
0.06384
1
0.748temperature...
0
0
1
-0.588outlook=rainy...
ma possiamo notare che, curiosamente, dal punto di vista entropico ha la
stessa importanza del quinto autovettore:
Ranked attributes:
0.675990846445273472
0.411301353536642624
0.195956514975330624
0.063841150150769192
0.000000000000000111
0.000000000000000111
1
2
3
4
6
5
0.578temperature...
-0.68outlook=overcast...
0.567outlook=sunny...
0.738windy...
-0.588outlook=rainy...
0.748temperature...
L’ultima prova che vogliamo effettuare riguarda la possibilità di effettuare il mapping inverso attraverso SVD nello spazio originale. Settiamo le
apposite opzioni e lanciamo la SVD. L’output è il seguente:
46
PC space transformed back to original space.
(Note: can’t evaluate attributes in the original space)
Ranked attributes:
1 3 outlook=rainy
1 1 outlook=sunny
1 2 outlook=overcast
1 6 windy
1 4 temperature
1 5 humidity
La nota, sebbene sembri allarmante, in verità fornisce un’informazione
alquanto intuitiva: la PCA non può ottenere esattamente lo spazio di partenza, semplicemente perchè abbiamo binarizzato la matrice (per quanto la
matrice non binarizzata potrebbe essere facilmente ricavata). In questo caso, non possiamo tagliare alcun autovalore nè autovettore, quindi l’eventuale
riduzione di dimensionalità è affidata per intero al ranker (che, in questo caso, non riesce a fare molto, essendo anche il dataset usato molto semplice e
piccolo).
47
Capitolo 4
Classificazione
Addentriamoci ora nel problema della classificazione di pattern. In questo capitolo supporremo di utilizzare sempre un dataset X, per il quale un
attributo è utilizzato come target. Ad ogni valore del target corrisponde una
classe. Tornando all’esempio weather considerato nei paragrafi 3.4 e 3.6, il
target è la variabile play, ovvero la decisione di giocare a golf o meno.
I problemi di classificazione si possono dividere in due sottocategorie,
come già avevamo visto nel paragrafo 1.2:
• si parla di classificazione binaria quando il target può assumere solamente due valori. Un esempio è il già citato weather : le due classi
corrispondono alla decisione di giocare o no a golf. Normalmente, i
target sono del tipo yi ∈ {0, 1} oppure yi ∈ {−1, 1};
• si parla di classificazione multiclasse quando il target può assumere
un numero finito di valori interi numerici, ovvero yi ∈ S ⊂ ℵ, dove ℵ
rappresenta l’insieme dei numeri naturali non negativi. Un esempio è il
dataset iris, sempre incluso tra gli esempi di WEKA, in cui tre tipi di
fiore vengono distinti sulla base delle caratteristiche di petalo e sepalo:
in questo caso, yi ∈ {1, 2, 3}, dove ogni classe corrisponde ad un preciso
fiore.
Alcuni algoritmi nascono nell’ottica della classificazione binaria: inizieremo con l’analisi per questo problema e mostreremo, quindi, le tecniche per
la generalizzazione al problema multiclasse.
48
4.1
4.1.1
Zero Rules
Apprendimento
Il classificatore Zero Rules (0–R) è davvero elementare: la classe viene
scelta sulla base della moda. Ciò significa che assegneremo ogni pattern a
run–time alla classe più ricorrente del nostro training set (in caso di parità, la
scelta avviene una volta per tutte randomicamente). Ovviamente, non è un
metodo particolarmente furbo nè utile, e spesso viene utilizzato nella pratica
solo per trovare le frequenze relative e assolute delle varie classi.
Supponendo di avere a disposizione un dataset X con 15 pattern e 3
classi, e ipotizzando di avere 7 pattern afferenti alla classe 2 e 4 pattern
ciascuno per le classi 1 e 3, sceglieremo la classe 2 in quanto moda del nostro
dataset.
4.1.2
Fase in avanti
La fase feedforward a run–time di 0–R consisterà semplicemente nell’assegnare la classe più frequente del training set ad ogni nuovo pattern che
arrivi in ingresso al nostro sistema.
4.1.3
Estensione al caso multiclasse
L’algoritmo Zero Rules si adatta già nella sua forma originaria a problemi
binari e multiclasse.
4.1.4
Esempio di analisi in WEKA
Torniamo a considerare il dataset weather. Lanciamo explorer di WEKA
e carichiamo il dataset. Ora, spostiamoci sul tab “Classify” in alto e selezioniamo come metodo di classificazione “ZeroR” nella sottocategoria “Rules”.
Aprendo la finestra delle opzioni, notiamo subito che l’unica opzione a disposizione si riferisce ad eventuali output di debug: settiamo a true. Tornando
ad explorer, nell’area “Test options” settiamo l’uso dell’intero training set
(le altre opzioni verranno presentate più avanti). Clicchiamo poi su “More
options” e abilitiamo “Output predictions”. Scelta la classe (play, nel nostro
caso), lanciamo l’analisi.
A parte un po’ di output di riepilogo, ci viene precisato che:
49
ZeroR predicts class value: yes
essendo yes la classe più ricorrente del nostro dataset. Passando ai risultati
successivi, analizziamo le voci che ci vengono fornite.
Predictions on training set
Viene presentato un riepilogo del comportamento del nostro classificatore
sul training set. Abbiamo a disposizione le seguenti voci:
• numero del pattern;
• valore reale della classe;
• valore ottenuto dal classificatore;
• un flag di errore corrispondente ai pattern per i quali sbagliamo la
previsione;
• la probabilità di indovinare la previsione. Tale calcolo coinvogle il pattern, il training set ed il particolare classificatore che usiamo. Il valore
più alto fra quelli a disposizione è contraddistinto da ‘*’.
(In)Correctly Classified Instances
Equivale al numero di classificazioni corrette o errate. A seguire, troviamo le percentuali relative al numero totale di pattern: nel nostro caso,
sbagliamo circa nel 36% dei casi.
Kappa statistic
La statistica Kappa [7] (anche nota come Kappa di Cohen o semplicemente Kappa) è basato su considerazioni statistiche e sull’uso di cosiddetti rater,
cioè valutatori. Rappresenta un metodo abbastanza rapido per valutare la
robustezza di un algoritmo. L’indice K viene calcolato come
K=
P (A) − P (E)
,
1 − P (E)
(4.1)
dove P (A) rappresenta l’accuratezza, ovvero la percentuale che il nostro predittore azzecchi, e P (E) è la probabilità che il classificatore indovini per pura
coincidenza:
50
nc
P (E) =
pi · qi ,
(4.2)
i=1
dove nc rappresenta il numero di classi, pi è la frequenza relativa di ogni classe
nel training set e qi è la frequenza relativa dell’output del nostro classificatore.
Vale K ∈ (−∞, 1]:
• K < 0 è indice di un classificatore che sbaglia volutamente;
• K = 0 rappresenta un classificatore che, quando indovina, lo fa per
puro caso;
• K = 1 è indice di massima robustezza del predittore.
Nel caso in esame, il nostro classificatore 0–R è caratterizzato da Kappa
nulla, il che mostra la scarsa affidabilità di 0–R. Controlliamo il risultato. Le
quantità che caratterizzano il nostro 0–R sono:
• P (A) ≈ 64.29% è l’accuratezza;
• p1 ≈ 64.29%, p2 ≈ 35.71%, q1 = 100% e q2 = 0%. Pertanto, P (E) ≈
64.29%.
Ne risulta, appunto, K = 0.
Mean absolute error
Rappresenta l’errore medio assoluto (MAE), quantità che nei problemi
di classificazione ha poca importanza. Comunque sia, esso è definito in questo caso come la distanza media tra la probabilità di classificazione corretta
e il target originario del dataset. In pratica, fornisce una misura complessiva del comportamento del classificatore relativa al particolare dataset che
utilizziamo.
Il MAE ha, invece, enorme importanza nei problemi di regressione, che
affronteremo a breve, in quanto in quei casi rappresenta la differenza media
tra l’output del nostro sistema e quello originario del dataset.
51
Root mean squared error
Per l’errore quadratico medio (RMSE) valgono molte delle considerazioni
fatte in precedenza per il MAE: infatti, il RMSE è calcolato (sia per regressione che per classificazione) come il MAE, tranne che ogni volta calcoliamo
il quadrato della differenza fra output (o probabilità) e valore originario.
Relative absolute error e Root relative squared error
Queste misure sono ottenute come rapporto, rispettivamente, fra MAE e
RMSE e i valori ottenuti col worst case, ovvero con un classificatore 0–R. Dato
che in questo caso usiamo un classificatore 0–R, non abbiamo miglioramenti
e l’errore relativo è pari al 100%.
Detailed Accuracy By Class e Confusion Matrix
Analizziamo ora i dati relativi alla tabella di accuratezza della previsione.
Otteniamo un output di questo tipo:
TP Rate
1
0
FP Rate
1
0
Precision
0.643
0
Recall
1
0
F-Measure
0.783
0
Class
yes
no
Prima di addentrarci nella spiegazione dei termini riportati, consideriamo
la matrice di confusione:
a b
<-- classified as
9 0 | a = yes
5 0 | b = no
La matrice di confusione (CM) va analizzata nel seguente modo: nelle
colonne, troviamo le classificazioni ottenute col metodo selezionato; nelle
righe, il numero di dati afferenti alle due classi nel training set. Spieghiamoci
meglio: nel nostro caso, abbiamo 9 dati, originalmente appartenenti alla
classe “yes”, che sono stati classificati come “yes”; abbiamo inoltre 5 dati
che nel training set appatrtenevano alla classe “no” (seconda riga), ma che
sono comunque stati classificati come “yes”. In Eq. (4.3), riportiamo un
esempio di confusion matrix CM con k classi, nel quale: Cii indica le caselle
contenenti il numero di dati della classe i correttamente classificati; Cij indica
52
il numero di dati appartenenti ad una classe i, ma erroneamente attribuiti
dal metodo alla classe j.
⎡
⎢
⎢
CM = ⎢
⎢
⎣
C11 C12 · · · C1k
C21 C22 · · · C2k
..
..
..
.
.
.
···
Ck1 Ck2 · · · Ckk
⎤
⎥
⎥
⎥.
⎥
⎦
(4.3)
Torniamo ora all’accuratezza per classe. Definita la CM, Analizziamo
voce per voce:
• iniziando dal fondo, “Class” indica la classe a cui i precedenti coefficienti sono riferiti: la prima riga si riferisce ai dati classificati come
classe “yes”, la seconda riga è riferita ai dati classificati come “no”;
• TP rate indica il True Positives rate, ovvero la percentuale dei dati
appartenenti alla classe c, i quali sono stati effettivamente classificati
in modo corretto. Nel nostro caso, il 100% dei dati afferenti alla classe
“yes” sono stati classificati correttamente, mentre nessun pattern è
stato classificato come “no”;
• FP rate indica il False Positives rate, ovvero la percentuale dei dati
appartenenti alla classe c, i quali sono stati classificati in modo errato.
Nel nostro caso, qualsiasi dato non afferente a “yes”, è stato comunque
classificato come “yes”, quindi il FP rate di questa classe è il 100%.
Viceversa, nessun pattern è stato classificato come “no”, quindi anche
il FP rate di questa classe è 0%;
• Precision indica la percentuale di dati, classificati come appartenenti
alla classe c, correttamente classificati in quella classe. Nel nostro caso,
il 100% dei dati “yes” sono stati correttamente classificati, mentre lo
0% dei “no” è stato attribuito a tale classe dallo 0–R;
• Recall è la parte di classe che è stata correttamente “scoperta”: coincide
quindi con il TP rate;
• la F–measure unisce Precision e Recall in un unico indice.
In termini formali, si può scrivere (i pedici c si riferiscono ad una generica
classe), riferendoci alla notazione di Eq. (4.3):
53
Ccc
T Pc = k
,
i=1 Cci
k
j=1 Ccj
F Pc = k
, ∀ j = c,
C
ci
i=1
Ccc
,
P recc = k
i=1 Cic
Recc = T Pc ,
2 · P recc · Recc
.
F mc =
P recc + Recc
4.2
(4.4)
(4.5)
(4.6)
(4.7)
(4.8)
Naive Bayesian Classifier
Terminata la rassegna sul poco utile classificatore 0–R, passiamo a qualche metodo più complesso ma anche decisamente più efficace. Iniziamo la
rassegna con il Naive Bayesian Classifier, anche noto come NBC.
4.2.1
Apprendimento
L’idea di base di NBC consiste nel classificare un dato sulla base del dato stesso, ovvero della probabilità di classe dato il pattern p (C = c |X = x),
dove C indica una variabile random per la classe, X un vettore di variabili random per gli attributi, c una particolare classe e x una particolare
osservazione. NBC si basa su due ipotesi semplificative:
1. tutte le feature sono indipendenti fra loro, data una classe;
2. non esistono attributi nascosti (e non presenti nel dataset) che influenzino in qualche modo il processo decisionale sulla classe.
Dato che spesso, nella realtà, queste due ipotesi sono tutt’altro che strettamente rispettate, le prestazioni del classificatore talvolta peggiorano.
Proseguiamo con l’analisi. Il teorema di Bayes ci dice che, dato un nuovo
pattern da classificare x, possiamo scegliere la classe sulla base delle seguenti
probabilità condizionali:
p (C = ci |X = x) =
p(C = ci )p (X = x |C = ci )
, ∀ i,
p (X = x)
54
(4.9)
scegliendo quindi la classe ci a probabilità maggiore. In questo caso, p(C =
ci ) rappresenta la probabilità a priori di classe, mentre
=
p (X = x |C = ci ) = p
j Xj = xj |C = ci
=
j p (Xj = xj |C = ci ) ,
(4.10)
avendo supposto indipendenti le feature data la classe. Inoltre, il termine
p (X = x) viene spesso trascurato, essendo soltanto un fattore di normalizzazione.
Il termine di Eq. (4.10) è facile da calcolare per variabili non continue;
nel caso di attributi continui, si può ipotizzare che la distribuzione di tali
valori sia gaussiana, ottenendo
p (Xj = xj |C = ci ) = 1
2πσj2
(xj − xj )2
exp −
2σj2
,
(4.11)
con xj e σj2 che rappresentano media e varianza dell’attributo xj , calcolate
sui pattern del training set. Di fatto, l’apprendimento si esaurisce nel calcolo
di media e varianza sul dataset usato per l’apprendimento. Una nota: in
alternativa all’Eq. (4.11), è possibile utilizzare un mapping non–lineare dei
dati attraverso funzioni kernel (che riprenderemo più avanti), le quali complicano la trattazione e non sono particolarmente didattiche al momento. Per
chi fosse interessato a maggiori dettagli, si veda [12].
4.2.2
Fase in avanti
La fase feedforward del NBC è stata già definita all’interno del paragrafo
sull’apprendimento: all’arrivo di un nuovo pattern, si utilizza l’Eq. (4.9) e si
sceglie la classe con probabilità condizionale più alta.
4.2.3
Estensione al caso multiclasse
Come risulta chiaro dalla trattazione e, in particolare, dall’Eq. (4.9),
NBC è nativamente multiclasse: è sufficiente iterare il calcolo della probabilità condizionale di classe su tutte i valori che il target può assumere.
55
4.2.4
Esempio di analisi in WEKA
Utilizziamo il nostro solito dataset, weather, e vediamo come si comporta
con NBC. Innanzitutto, da WEKA explorer, selezioniamo il classificatore
“NaiveBayes” dalla sottocategoria “Bayes”. Il classificatore permette tre
personalizzazioni:
1. alcuni ulteriori output di debug (si possono attivare o no);
2. passare ad un mapping non–lineare attraverso kernel dei nostri ingressi
(lo lasceremo a false in questa analisi);
3. rappresentare le variabili continue non attraverso una distribuzione normale, ma attraverso una discretizzazione dell’attributo in appositi intervalli (di fatto, rendere la variabile discreta o, se vogliamo, qualitativa).
Anche in questo caso, lasceremo false questa opzione.
Appurandoci di effettuare il training su tutto il training set e, se vogliamo,
avendo attivato l’uscita di tipo probabilistico, lanciamo l’analisi.
In questo caso, abbiamo ben 13 classificazioni esatte su 14 pattern di training, valori medi di errore bassi e una Kappa elevata (sopra lo 0.8). Premesso
che per un test più accurato è necessario l’utilizzo di dati non appartenenti
al training set, i valori che ritroviamo sono decisamente incoraggianti. Anche
la CM è:
a b
<-- classified as
9 0 | a = yes
1 4 | b = no
ovvero l’unico errore è un “no” che classifichiamo come “yes”. Quantomeno
abbiamo cominciato a distinguere due classi, è già un bel passo in avanti.
4.3
4.3.1
Reti neurali: MultiLayer Perceptrons
Cenni storici: il percettrone
Prima di lanciarci nell’analisi del percettrone multistrato, è bene cominciare a capire cosa sia un percettrone. Introdotto da Rosenblatt nel 1958
[21], esso rappresentava per l’epoca un’innovazione incredibile: in pratica,
56
esso consisteva in una funzione matematica in grado di “imparare” dai dati
attraverso un algoritmo di apprendimento vero e proprio. Infatti, fino ad ora,
sia 0–R sia NBC non effettuano un vero e proprio learning dai dati: il primo
fa un semplice conto sulla frequenza, il secondo al massimo calcola media e
varianza per fittare una gaussiana.
Il percettrone è un classificatore binario che mappa i suoi ingressi x ∈ m
in un valore scalare y = f (x) ∈ , calcolato come
y = f (x) = χ (w · x + b) ,
(4.12)
dove w è un vettore di pesi da applicare agli ingressi, b è detto bias ed è
un termine costante che non dipende dagli ingressi, e χ(z) è la funzione di
attivazione. Le scelte più comuni per χ(z) sono:
χ(z) = Θ(z)
(4.13)
χ(z) = z Θ(z)
(4.14)
χ(z) = tanh(z)
1
χ(z) =
1 + e−z
χ(z) = z,
(4.15)
(4.16)
(4.17)
dove Θ(z) è la cosiddetta funzione Heaviside:
⎧
⎪
⎨ 0
Θ(z) =
⎪
⎩
se
se
se
1
2
1
z<0
z=0 .
z>0
(4.18)
Non è raro vedere riformulata l’Eq. (4.12) come
·x
) ,
y = f (x) = χ (w
(4.19)
esattamente equivalente all’Eq. (4.12), ma nella quale abbiamo aggiunto
al vettore dei pesi il termine del bias e al vettore degli ingressi un termine
costante a 1. Uno schema grafico del percettrone è presentato in Fig. 4.1.
L’algoritmo di apprendimento è iterativo di tipo error backpropagation
(BP ), ovvero la differenza tra l’uscita reale e quella ottenuta dal percettrone
ad ogni passo viene usata come feedback per adattare i pesi. Sfortunatamente, il percettrone riusciva a riconoscere dopo l’addestramento solamente
57
Figura 4.1: Schema grafico di un percettrone.
funzioni linearmente separabili, ovvero senza sovrapposizione fra le classi (le
Figg. 4.2 e 4.3 mostrano due esempi di dataset linearmente e non linearmente separabili): in particolare, Minsky e Papert [16] mostrarono che il
percettrone non era in grado di apprendere nemmeno l’elementare funzione
logica XOR. Questo perchè, come mostrato in Fig. 4.4, lo XOR non è un
problema linearmente separabile (i simboli ‘x’ mostrano le uscite a 1 e i ‘o’
rappresentano gli output a 0).
8
6
4
2
0
−2
−4
−6
−8
−8
−6
−4
−2
0
2
4
6
8
Figura 4.2: Esempio di due classi di dati linearmente separabili.
Dopo, quindi, un iniziale straordinario successo, il percettrone rimase
58
2
1.5
1
0.5
0
−0.5
−1
−1.5
−2
−2
−1.5
−1
−0.5
0
0.5
1
1.5
2
Figura 4.3: Esempio di due classi di dati non linearmente separabili.
1.5
1
0.5
0
−0.5
−0.5
0
0.5
1
1.5
Figura 4.4: Rappresentazione grafica della funzione logica XOR.
59
quasi inutilizzato per una decina d’anni, fino a quando non vennero sviluppate
le cosiddette reti multistrato, cioè le MLP.
4.3.2
Architettura di un MLP
La struttura generale di un MLP è costituita da tre strati di neuroni:
1. il primo strato viene detto input layer ed è in contatto diretto con i
dati di ingresso;
2. lo strato intermedio viene detto hidden layer e non ha contatti diretti
con l’esterno, in quanto riceve i dati dall’input layer e li invia allo strato
di neuroni di uscita;
3. l’ultimo livello è l’output layer, il quale riceve i dati dai neuroni dello
strato intermedio e si interfaccia con l’uscita.
Dato che, spesso, per la rappresentazione del MLP si utilizzano grafi, si parla di topologia di una rete, in alternativa al più classico termine architettura
della rete. Un esempio di MLP è presentato in Fig. 4.5. Talvolta, lo strato
hidden è assente e i layer di ingresso ed uscita coincidono: si parla in quel
caso di Single Layer Perceptron, ma non analizzeremo questo tipo di rete.
Il layer hidden può, inoltre, contenere diversi layers al proprio interno. Il
MLP rappresenta il primo esempio di Artificial Neural Network o più semplicemente Rete Neurale (NN) che abbia avuto davvero successo, anche dal
punto di vista pratico.
Iniziamo a considerare l’architettura di un MLP: supponiamo che esso
contenga, al proprio interno, n neuroni nell’input, h nell’hidden e p neuroni
nell’output layer. I pesi wik , con i = 1, ..., n e k = 1, ..., h, permettono
l’interfacciamento fra i neuroni di input e quelli di hidden; i pesi zkj , con k =
1, ..., h e j = 1, ..., p, connettono i neuroni di hidden con quelli di output. Per
quanto riguarda la determinazione del numero di neuroni e strati per l’hidden
layer, non esiste un metodo preciso in letteratura, ma di solito si procede
ad un confronto fra architetture per scegliere quella ottimale. I neuroni di
hidden, quindi, ricevono informazione dai neuroni di input attraverso i pesi w,
e producono l’uscita hk = f (x, wk ), dove f (·) è la funzione di attivazione del
neurone. I neuroni di output, a loro volta, ricevono i dati dall’hidden layer,
60
Figura 4.5: Esempio di architettura di un MLP
vi applicano gli opportuni pesi z e quindi producono l’output yj = g(h, z j ).
Unendo le due funzioni, l’uscita del j–esimo neurone è quindi:
yj = g
hk zkj
=g
k
k
zkj f
xi wik
.
(4.20)
i
Questa equazione mostra come il mapping degli ingressi in un MLP sia
altamente non lineare. È, però, necessario trovare i pesi che caratterizzano
la rete. Possiamo identificare tre tipi di MLP:
• MLP con pesi fissati: di fatto, non contemplano una fase di apprendimento, ma i pesi vengono determinati sulla base di informazioni a
priori. Non ci occuperemo di questo tipo di reti, in quanto davvero
poco usate;
• Supervised learning MLP: nel training set abbiamo definito un target
e, quindi, è possibile definire una funzione di errore rispetto all’output
ottimo;
• Unsupervised learning MLP: anche note come Self Organizing Maps o
Mappe di Kohonen, dal nome di chi le ha introdotte, non prevedono la
definizione di un target nel training set. Sono abbastanza usate, ma
per motivi di tempo non ce ne occuperemo. Per chi fosse interessato,
[15] può risultare utile.
61
Come anticipato nelle precedenti righe, ci concentreremo in queste dispense solo sui Supervised learning MLP, per i quali analizziamo l’algoritmo
per l’apprendimento.
4.3.3
Apprendimento
L’algoritmo di learning in assoluto più usato è la già citata backpropagation (BP ). Iniziamo a definire la funzione errore per il j–esimo nodo; per
esempio, possiamo scegliere:
ej = dj − yj ,
(4.21)
nella quale dj rappresenta il target voluto e yj l’uscita della nostra rete.
Possiamo definire la funzione energia, che nel nostro caso risulta essere:
E=
1 2
e.
2 j j
(4.22)
Attraverso l’errore, e quindi attraverso yj , la funzione energia dipende
dai nostri pattern di training in maniera altamente non lineare, come appare
chiaro dall’Eq. (4.20). Al fine di trovare i pesi ottimi, quindi, siamo costretti
a ricorrere ad un algoritmo di tipo iterativo, appunto come la BP, col pericolo
peraltro di ritrovarci bloccati in qualche minimo locale.
Supponiamo di inizializzare i pesi della rete con valori random, trovando
(s)
(0)
w . Definiamo l’errore allo step s come ej . Dalla teoria dei differenziali,
si può dimostrare che il passo di aggiornamento per i pesi è
(s)
(s) (s)
Δwji = ηδj yi ,
(4.23)
(s)
nella quale δj è
(s)
δj = −
(s)
∂E (s)
(s)
∂υj
(4.24)
dove υj è l’output del neurone j allo step s, e η ∈ [0, 1] è il cosiddetto
learning rate, che è un parametro da fissare prima di iniziare l’apprendimento.
Proprio per questo motivo, più che un vero e proprio parametro, è considerato
un iperparametro, ovvero una quantità da stabilire come trial and error e
che determina il comportamento globale dell’algoritmo. Se troppo piccolo,
l’algoritmo converge molto lentamente; se troppo grande, l’algoritmo inizia
62
ad oscillare, divenendo instabile. Normalmente, 0.2 < η < 0.8 in molte
applicazioni pratiche.
(s)
Il valore di δj può essere calcolato in maniera differente a seconda che
il j–esimo neurone faccia parte dell’output o dell’hidden layer. Se j è un
neurone di output, è facile dimostrare che vale:
(s)
υj
(s)
(s)
(s)
δj = ej χ υj ,
(4.25)
che rappresenta la derivata prima della funzione attivazione.
con χ
Se, invece, ci occupiamo di un neurone dell’hidden layer, otteniamo:
(s)
δj
(s)
(s) (s)
= χ υj
δk wkj .
(4.26)
k
Dato che la precedente formula dipende da wkj , essa è anche dipendente dalle
variazioni dei pesi nel nodo k. In questo appare chiaro il significato della BP.
A volte, può aiutare la convergenza l’aggiunta di un altro termine all’Eq. (4.23), ovvero del cosiddetto momento m ∈ [0, 1]: sfortunatamente,
anch’esso è un iperparametro ed è estremamente difficile settarne il valore
ottimo, quantomeno a priori. Anche per il momento valgono le considerazioni fatte per η, ovvero normalmente 0.2 < m < 0.8. L’Eq. (4.23) risulta cosı̀
modificata:
(s)
(s) (s)
(s−1)
Δwji = ηδj yi + mΔwji
.
(4.27)
Un altra difficoltà consta nel criterio di stop da utilizzare per bloccare
l’algoritmo. I metodi più utilizzati sono:
• stabilire un numero massimo di iterazioni;
• fissare un tempo massimo di esecuzione;
• fermare l’algoritmo se l’errore scende sotto una soglia predeterminata;
• stop se il valore dell’errore per un certo numero di step non scende oltre
un valore prefissato;
• utilizzare come parametro l’errore su un validation set (ne discuteremo
nel paragrafo 4.3.6).
63
4.3.4
Fase in avanti
Una volta trovati e salvati i pesi, la fase in avanti è semplicemente realizzata attraverso l’Eq. (4.20), nella quale vengono applicati i pesi trovati con
la BP.
4.3.5
Estensione al caso multiclasse
L’estensione al caso multiclasse è particolarmente semplice: è sufficiente
inserire tanti neuroni nello strato di output quante sono le classi del nostro
problema. Per esempio, un problema di classificazione binaria avrà due neuroni di uscita, un problema multiclasse con 5 classi avrà 5 neuroni di uscita.
Qualora più di un neurone di uscita sia attivato, il neurone con output analogico maggiore vince e la classe viene assegnata di conseguenza: questa viene
anche detta tecnica Winner–Take–All (WTA).
4.3.6
Esempio di analisi in WEKA (I)
Consideriamo nuovamente il dataset weather. Da WEKA explorer, selezioniamo il classificatore “MultiLayerPerceptron”, che possiamo trovare nella sottocategoria “functions”. WEKA utilizza solo funzioni di attivazione
di tipo sigmoidale, come da Eq. (4.16). Analizziamo le opzioni a nostra
disposizione:
• “GUI” permette di utilizzare un’interfaccia grafica per visualizzare la
rete creata. Se settato a false, attiviamolo;
• “autobuild”, se attivato, consente a WEKA di modificare i neuroni di
hidden in maniera automatica. Spesso utile, conviene mantenere su
true l’opzione;
• “debug” è la solita opzione per eventuali output di debug;
• “decay” consente a WEKA di abbassare iterativamente il learning rate
nel caso di reset della rete (vedi sotto). Settiamolo in queste prove a
false;
• “hiddenLayers” rappresenta il numero di neuroni hidden. Esistono
alcune wildcards per questo valore:
64
– a=
#attributi+#classi
;
2
– i = #attributi;
– o = #classi;
– t = 2 · a;
• “learningRate” e “momentum” sono le quantità η e m di cui abbiamo
parlato nel paragrafo 4.3.3. In queste prove, li lasceremo pari ai valori
di default, cioè η = 0.3 e m = 0.2;
• “nominalToBinary” è utilizzato per binarizzare la matrice dei dati nel
caso di variabili qualitative (per noi, true);
• “normalizeAttributes” viene utilizzato per normalizzare le feature tra
[−1, 1]. Anche in questo caso setteremo true;
• “normalizeNumericClasses” normalizza i valori numerici dei target tra
[−1, 1] (true);
• “randomSeed” è il seed per l’algoritmo di random per la selezione del
punto di partenza e per lo shuffling dei dati (settiamo seed pari a 16,
un numero casuale ma che ci permette analisi consistenti);
• “reset” consente all’algoritmo di resettare la rete nel caso durante l’esecuzione il valore delle uscite tenda a divergere rispetto al target voluto.
Settiamolo a false;
• “trainingTime” fissa il criterio di stop sul numero massimo di iterazioni
da eseguire. Settiamolo a 1000;
• “validationSetSize” e “validationThreshold” vengono utilizzati come
criterio di stop in alternativa al numero di iterazioni. Il primo valore, se diverso da 0, fissa percentualmente il numero di pattern del
training set che non verranno utilizzati per trovare i pesi. Una volta
trovati i pesi coi restanti pattern, la rete verrà testata sul validation
set e verrà trovato un errore. Tale errore scenderà per un certo numero di iterazioni, poi la rete tenderà ad overfittare (in generale) e
l’errore tenderà a salire: “validationThreshold” fissa dopo quante iterazioni consecutive con peggioramento dell’errore dobbiamo fermarci.
65
Per il momento, manteniamo disattivato tale criterio di stop, fissando
“validationSetSize” a 0.
Figura 4.6: Esempio di GUI di WEKA per le reti neurali MLP.
Passate in rassegna le opzioni, lanciamo la nostra analisi. Si aprirà in
automatico una finestra come quella di Fig. 4.6. Notiamo che l’input layer
è rappresentato direttamente con nodi aventi il nome degli attributi (le variabili qualitative sono state binarizzate); avendo settato ad a il valore degli
hidden layers, abbiamo a = (6 + 2)/2 = 4 neuroni di hidden. Mediante apposito pulsante, lanciamo l’analisi. Una volta terminata, chiudiamo la GUI e
accettiamo il modello cosı̀ trovato. Torneremo ora ad explorer, che ci mostra
i pesi e i bias dei neuroni e le caratteristiche statistiche del classificatore.
Notiamo che non commettiamo errori, i valori di MAE e RMSE sono
molto bassi, tanto da apportare il 95% circa di miglioramento in termini di
errore rispetto a 0–R. Anche la Kappa è massima, essendo pari a 1.
4.3.7
Esempio di analisi in WEKA (II)
Manteniamo le stesse opzioni, ma cambiamo dataset e complichiamo un
po’ la vita al MLP. Scegliamo come dataset iris, composto da 150 pattern,
4 feature (riguardanti le dimensioni di sepalo e petalo) e un target (3 classi
per 3 tipi differenti di fiori).
66
Proviamo a lanciare l’analisi con NBC e vediamo come si comporta. Il
classificatore bayesiano commette 6 errori, pari al 4%, ha un’ottima Kappa
(0.94) e si comporta egregiamente in termini di MAE e RMSE (in questo
caso, miglioriamo però “solo” del 70% rispetto allo 0–R). Proviamo con il
MLP. Questa volta, commettiamo solo 2 errori (1.33%), la Kappa è anche
migliore (0.98) e il miglioramento percentuale del RMSE è circa pari all’82%.
Proviamo ad utilizzare ora una nuova opzione, finora mai utilizzata. In
WEKA explorer, nell’area “Test options”, settiamo di splittare il dataset a
nostra disposizione in un training set, composto dal 67% dei dati (100 pattern), e un validation set, sul quale confronteremo le performance di NBC
e MLP. Lanciamo le analisi con i due classificatori. Questa volta confronteremo solo l’errore sul validation set. NBC commette 2 errori (4%), contro
un solo errore (2%) del MLP, che quindi, utilizzando questo criterio, sembra
avere una migliore performance.
4.3.8
Validation set e test set
Quando abbiamo introdotto nel paragrafo 1.2 i termini dataset e training
set, abbiamo anticipato che ci saremmo occupati solo più avanti di validation
e test set.
Il validation set è un insieme di dati, indipendenti da quelli del training
set, che possono essere utilizzati per stimare le performance di un modello,
trovato usando solo il training set. Nel caso precedente, abbiamo effettuato l’apprendimento su 100 dati e poi abbiamo verificato le performance sui
restanti 50, costituenti appunto il validation set. L’utilizzo di un validation
set si rende necessario quando vogliamo confrontare diversi metodi statistici (ad esempio, NBC e MLP) oppure verificare le performance al variare di
parametri e/o iperparametri. Ad esempio, potremmo verificare su iris come
cambiano le performance portando momento e learning rate entrambi a 0.8:
l’errore in termini percentuli resta uguale, ma con i due iperparametri settati
a valori più alti sale leggermente il RMSE.
Il test set, infine, è un terzo set di dati, indipendente da validation e
training set, che viene utilizzato alla fine solo dopo aver scelto il modello definitivo, come banco di prova prima dell’implementazione della fase in
avanti. Il test set viene utilizzato, quindi, solo su un metodo statistico, quello
prescelto utilizzando (per esempio) il validation set.
67
Occorre prestare molta attenzione, perchè spesso in rete, in letteratura e
anche in WEKA si fa molta confusione: la nomenclatura presentata in questo
paragrafo va tenuta come riferimento all’interno di questo insegnamento.
4.4
4.4.1
Support Vector Machines
Il problema del classificatore a massimo margine
Abbiamo analizzato nel precedente paragrafo pregi e difetti dei MLP: a
fronte di una classificazione efficace, l’apprendimento tramite BP è alquanto
problematico, a partire dal fatto che il problema da risolvere non è convesso
e può presentare miriadi di minimi locali.
Mentre molti studiosi tra Stati Uniti ed Europa dibattevano negli anni
’60 e ’70 su percettrone, XOR e MLP, in Unione Sovietica due matematici,
Vapnik e Chervonenkis, svilupparono una teoria, detta Statistical Learning
Theory (SLT ), che avrebbe trovato definitiva applicazione solo nella seconda
metà degli anni ’90 e che avrebbe rivoluzionato il mondo delle reti neurali. L’idea si basa su due concetti fondamentali, che già in parte abbiamo
analizzato:
1. un classificatore dev’essere sufficientemente complesso da riuscire a classificare efficacemente set di dati anche particolarmente mal posizionati;
2. tale classificatore non deve essere, però, troppo complicato, altrimenti
si subirebbero gli effetti dell’overfitting.
Dal bilanciamento dei punti 1 e 2 otteniamo il classificatore ottimo, che
si può dimostrare essere il cosiddetto classificatore a massimo margine. Il
concetto più innovativo della teoria di Vapnik consta proprio nella definizione
del concetto di margine, ovvero di distanza fra i punti di due classi (per ora,
poniamoci nel caso biclasse) più vicini fra loro. L’illustrazione grafica di Fig.
4.7 dovrebbe chiarire costa intendiamo per margine: abbiamo preso due set
di dati di due classi linearmente separabili e abbiamo tratteggiato i limiti del
margine massimo.
Nacque cosı̀ la Support Vector Machine (SVM ): spiegheremo meglio a
tempo debito il significato di questo nome. L’iniziale scarso successo della
SVM è dovuto a diversi fattori: innanzitutto, la teoria è stata sviluppata in
68
8
6
4
2
0
−2
−4
−6
−8
−10
−6
−4
−2
0
2
4
6
Figura 4.7: Esempio di dataset linearmente separabile. Tratteggiati, abbiamo
rappresentato i limiti del massimo margine ottenibile.
piena Guerra Fredda nell’URSS, quindi non è stata volutamente divulgata “al
di qua di Trieste”, per dirla con Churchill; in secondo luogo, la SVM presentava non pochi problemi pratici. Per realizzare, infatti, l’obiettivo di evitare
l’overfitting, era stata sviluppata una teoria, detta di Vapnik–Chervonenkis
o VC Theory, che permetteva di calcolare il grado di complessità di una famiglia di classificatori, ma in maniera tutt’altro che pratica. Inoltre, la versione
originale di SVM era in grado di trattare solo dataset linearmente separabili.
Fu solo negli anni ’90, al termine della Guerra Fredda, che Vapnik iniziò a
lavorare negli USA presso il laboratorio di ricerca della AT&T e, grazie al fondamentale aiuto di Corinna Cortes, nacque la SVM cosı̀ come la conosciamo
oggi [23, 8].
Consideriamo un dataset {(x1 , y1 ), ...., (xl , yl )}, dove xi ∈ m e yi =
±1. La formulazione originaria di SVM (pre–Cortes, potremmo dire) è la
seguente:
min
w ,b
1
w2
2
yi (w · x + b) ≥ 1 ∀i ∈ [1, . . . , l]
69
(4.28)
(4.29)
dove w è un vettore di pesi, b è il bias e il piano (o, a più dimensioni,
l’iperpiano) separatore tra le due classi è descritto dall’equazione
w · x + b = 0,
(4.30)
analogamente a quanto visto per il percettrone. Si può dimostrare che il margine è pari a 1/w2 , quindi andiamo a massimizzarlo attraverso il problema
di minimo vincolato (4.28).
Il problema, in molti casi pratici, consisteva nel fatto che il vincolo (4.29)
era tutt’altro che facile da rispettare, perchè prevedeva che non vi fosse sovrapposizione fra classi. L’idea fondamentale in questo senso è stata l’introduzione di variabili di slack ξi ≥ 0, che permettessero ad alcuni dati di violare
il vincolo. La formulazione, detto problema primale di SVM, è la seguente:
min
w ,b,ξ
1
w2 + CeT ξ
2
yi (w · x + b) ≥ 1 − ξi
(4.31)
∀i ∈ [1, . . . , l]
ξi ≥ 0 ∀i ∈ [1, . . . , l]
(4.32)
(4.33)
con ei = 1, ∀i, e eT ξ che rappresenta quindi la somma degli errori che commettiamo nella classificazione del training set. C è un iperparametro che
bilancia la componente di massimizzazione del margine (tendenza all’underfitting) e quella di minimizzazione dell’errore (tendenza all’overfitting).
L’analisi sarebbe, quindi, completa, se non fosse per il fatto che il problema (4.31) è tutt’altro che banale da risolvere. Fortunatamente, utilizzando la
tecnica dei moltiplicatori di Lagrange, introducendo l moltiplicatori αi (uno
per pattern), si ottiene il cosiddetto problema duale di SVM :
min
α
1 T
α Qα + r T α
2
0 ≤ αi ≤ C ∀i ∈ [1, . . . , l]
(4.35)
yT α = 0
(4.36)
(4.34)
dove ri = −1, ∀i, e Q = {qij } ∈ l×l è una matrice simmetrica semidefinita
positiva:
qij = yi yj K(xi , xj ),
70
(4.37)
Kernel
Lineare
Polinomiale
Gaussiano
Funzione
K(xi , xj ) = xi · xj
K(xi , xj ) = (xi · xj + 1)p
K(xi , xj ) = exp −γ xi − xj 22
Tabella 4.1: Funzioni kernel più comuni.
nella quale K(xi , xj ) è detta funzione kernel ed effettua un mapping non
lineare degli ingressi in uno spazio (in generale) a maggiore dimensionalità,
dove la classificazione dovrebbe essere più semplice. In poche parole, la
SVM classifica i dati mediante un separatore lineare, esattamente come il
nostro buon vecchio percettrone, ma in uno spazio in cui tale classificazione
è più semplice; in tale spazio i dati vengono mappati attraverso i kernel. Le
funzioni kernel più comuni sono quelle presentate in Tab. 4.1: nel caso di
kernel gaussiano e polinomiale, possiamo notare l’introduzione di un ulteriore
iperparametro oltre a C, rispettivamente γ e p, che regolano l’ampiezza della
gaussiana e il grado del polinomio classificatore.
Torniamo al problema (4.34): il grande successo di SVM è dovuto al fatto
che il problema duale è un cosiddetto Constrained Convex Quadratic Problem
(CCQP), ovvero, essendo convesso, esso ha una sola soluzione ottima e non
presenta minimi locali. Rispetto ai MLP questo è un vantaggio enorme: se
anche in SVM abbiamo uno (o più) iperparametro(/i) da settare, essi non
determinano la possibilità di trovare o meno una soluzione, solo stabiliranno
una maggiore o minore qualità di tale soluzione.
4.4.2
Apprendimento
La fase di training di SVM consta nel risolvere il problema duale e trovare i moltiplicatori di Lagrange ottimi α e il bias b che, per quanto non
appaia in forma esplicita in (4.34), ci è necessario poi per la fase in avanti. Per risolvere il problema duale sono state sviluppate moltissime tecniche,
ma la più usata è la cosiddetta Sequential Minimal Optimization (SMO): il
CCQP viene decomposto in tanti problemi elementari, in cui viene trovata
la soluzione per due pattern per volta. È necessario trovare la soluzione per
due pattern semplicemente a causa della presenza del vincolo di uguaglianza
71
di Eq. (4.36), per il quale ad ogni “spostamento” di un αi deve corrispondere
un’altra modifica di un altro parametro.
SMO si ferma (in quanto ha trovato la soluzione ottima) nel momento
in cui sono rispettati tutti i vincoli di ottimalità (a meno di una prefissata
precisione di macchina), detti condizioni di Karush–Kuhn–Tucker o KKT.
Per semplicità e brevità, non presentiamo in questo testo le KKT, per le
quali è necessario esplicitare il passaggio da problema primale a duale: per
chi fosse interessato, consigliamo [6]. Le KKT, oltre a fornire la soluzione
ottima α, consentono anche di calcolare il bias, considerando che l’iperpiano
separatore normalmente (anche se, in teoria, non sarebbe obbligatorio) viene
posto a metà del margine. Ad esempio, recuperando l’esempio di Fig. 4.7, il
piano separatore è quello di Fig. 4.8.
8
6
4
2
0
−2
−4
−6
−8
−10
−6
−4
−2
0
2
4
6
Figura 4.8: Esempio di piano separatore: tratteggiati, i limiti del margine;
con tratto breve–lungo, il piano separatore.
Una nota conclusiva: dato che la matrice Q ∈ l×l , la SVM soffre grandi
dimensioni non in termini di numero di feature, bensı̀ in termini di numero
di pattern. Per questo, spesso, una feature selection applicata prima di SVM
spesso non risolve alcun problema e, anzi, talvolta peggiora la qualità della
classificazione.
72
4.4.3
Fase in avanti
La fase in avanti consiste nel verificare il segno della funzione che descrive
il piano separatore. In termini di problema primale, supponendo target del
tipo yi = ±1, la classificazione di un nuovo pattern x avviene tramite:
y = ϑ (w · x + b) ,
(4.38)
dove la funzione ϑ(·) è definita come:
⎧
⎪
⎨ +1
ϑ(z) =
−1
⎪
⎩
random(±1)
se
se
se
z>0
z<0 .
z=0
(4.39)
Sfortunatamente, risolvendo il problema duale non possiamo conoscere
esplicitamente i pesi w. Si può dimostrare che la forma nel duale per la
funzione di classificazione è la seguente:
y=ϑ
l
yi αi K (x, xi ) + b ,
(4.40)
i=1
per la quale conosciamo ogni termine. In pratica, i coefficienti αi pesano
quanto ogni dato del training set sia di supporto alla decisione finale, ovvero
al calcolo del target stimato y, come appare evidente dall’Eq. (4.40): da qui,
il nome Support Vector Machine, ovvero macchina a supporto vettoriale.
4.4.4
Estensione al caso multiclasse
Al contrario dei metodi fin qui analizzati, l’estensione al caso multiclasse
per SVM non è banale. Tralasciando moltissime tecniche, seppur interessanti,
le più comunemente utilizzate sono la One Vs. All (OVA) e la All Vs. All
(AVA).
La tecnica OVA prevede che vengano istruite tante SVM in maniera tale
che ognuna delle classi venga distinta dalle altre mediante un problema binario. In pratica, supponendo di avere k classi, dovremo istruire k SVM (classe
1 vs. le altre, classe 2 vs. le altre,...) e attribuiremo un nuovo pattern alla
classe risultante dalle classificazioni binarie o, in caso di incertezza, alla classe con output analogico più alto. Per output analogico di SVM intendiamo
il valore
73
f (x) =
l
yiαi K (x, xi ) + b
(4.41)
i=1
che passiamo alla funzione ϑ(·).
La tecnica AVA, invece, crea tante SVM binarie in modo tale che ogni
classe venga distinta contro ognuna delle altre classi. Supponendo di avere,
quindi, 3 classi avremo: 1 vs. 2, 1 vs. 3 e 2 vs. 3, per un totale di 3
classificatori. Il problema consta nel fatto che, al crescere del numero di
classi, il numero di classificatori necessari esplode, essendo pari a k(k − 1)/2.
Tuttavia, AVA talvolta offre performance migliori rispetto a OVA ed è quindi
un’opzione valida se k è piccolo. È la tecnica utilizzata per la classificazione
multiclasse da WEKA.
Un’altra tecnica è l’Augmented Binary [2], che prevede la modifica del
dataset di training in modo tale da trasformarlo in un problema binario
risolvibile con una sola SVM (a fronte, però, di un aumento di dimensionalità
sia in termini di pattern che di feature): non approfondiremo, però, questa
tecnica.
4.4.5
SVM e la probabilità
Facciamo un passo indietro e torniamo ai problemi binari. Spesso, una
uscita di tipo digitale ±1 può non essere sufficiente. Supponiamo di considerare il caso di una SVM utilizzata per identificare se un paziente in un
ospedale è malato o no: se voi foste il paziente, vi basterebbe un’uscita digitale o vorreste anche conoscere la probabilità di tale uscita, ovvero (in un
certo senso) il grado di sicurezza di tale output? Decisamente, un’uscita di
tipo probabilistico è spesso necessaria.
Una tecnica per “convertire” l’output analogico di SVM di Eq. (4.41) in
un valore di tipo probabilistico è stata proposta da Platt [18]: la probabilità
di errore pe di classificazione per un pattern verrà fornita attraverso l’utilizzo
di una sigmoide
1
pe (x) =
,
(4.42)
1+
dove A e B sono due parametri che vengono fissati risolvendo un problema
di Maximum Likelihood. Non approfondiremo oltre questo argomento.
eAf (x)+B
74
4.4.6
Esempio di analisi in WEKA
Lanciato WEKA explorer, carichiamo il dataset weather, tanto per iniziare, e quindi spostiamoci sui tool di classificazione. Vogliamo iniziare con
un kernel lineare. Nella sottocategoria “functions” troviamo la SVM sotto le
mentite spoglie del nome SMO (SVM è un marchio registrato). Analizziamo
le principali opzioni:
• “buildLogisticModel” consente di ottenere l’uscita in termini probabilistici, utilizzando il metodo di Platt del paragrafo 4.4.5. Per ora,
settiamolo a false;
• “c” è il valore dell’iperparametro C. Settiamolo a 1;
• “cacheSize” è la dimensione della cache per la memorizzazione della
matrice Q;
• “debug” rappresenta eventuali output di debug;
• “epsilon” rappresenta lo zero di macchina per la rappresentazione di
coefficienti, bias, ecc. Conviene lasciarlo invariato;
• “exponent” è l’esponente p del kernel polinomiale. Settiamolo a p = 1;
• “featureSpaceNormalization” permette di effettuare la normalizzazione
dei dati nello spazio non lineare descritto attraverso le funzioni kernel.
Per ora, lasciamolo a false;
• “filterType” permette di applicare filtri ai dati. Settiamolo sulla normalizzazione del training set;
• “gamma” è il valore di γ per il kernel gaussiano. Settiamo γ = 1;
• “lowOrderTerms” include o meno il termine ‘+1’ nel kernel polinomiale.
Per le definizioni di Tab. 4.1, setteremo questo parametro a false se
usiamo un kernel lineare e a true se il grado del polinomio p è più
grande di 1. Per ora lasciamolo a false;
• “numFolds” permette di utilizzare la cross validation (la analizzeremo
nei prossimi capitoli) per cercare i valori di A e B per la sigmoide della
probabilità. Settiamo il valore −1 per disattivare l’opzione;
75
• “randomSeed” è il seed della funzione random per mescolare i dati
prima dell’eventuale cross validation;
• “toleranceParameter” è la tolleranza per il rispetto delle KKT. Il valore
di default 10−3 è un buon valore;
• “useRBF” è un flag per utilizzare il kernel gaussiano (per ora, false).
Lanciamo l’analisi su tutto il training set. Notiamo che commettiamo
2 errori, l’errore medio è abbastanza elevato e la Kappa è buona ma non
eccezionale (0.68). Notiamo un peggioramento rispetto al MLP: questo perchè il MLP è nativamente non lineare, mentre noi abbiamo applicato una
classificazione lineare.
Settiamo “useRBF” a true e lasciamo invariati gli altri parametri: notiamo che l’errore si annulla del tutto e abbiamo una Kappa massima. Di
fatto, abbiamo il nostro classificatore ideale.
Mettiamo alla prova ora SVM con iris, e torniamo ad un kernel lineare.
WEKA utilizza il metodo AVA per gestire il problema multiclasse. Utilizziamo l’intero training set, per il momento. Commettiamo 5 errori, e la Kappa
e l’errore medio si pongono a metà tra MLP e NBC. Questa volta, anche con
un kernel gaussiano le cose non vanno meglio: sembrerebbe quindi il MLP
l’ottimo per iris. Lasciamo C = 1, ma settiamo γ = 100: otteniamo 0 errori
e nuovamente il classificatore ottimo che cercavamo. È stato sufficiente agire
un po’ sugli iperparametri per trovare una soluzione molto buona.
Con l’ultima configurazione usata, lanciamo l’analisi su 100 pattern di
training e vediamo come si comporta la SVM sui 50 rimanenti di validation. Commettiamo 3 errori, quindi avremmo la peggiore performance fra i
3 metodi. Settando γ = 10, però, si possono ottenere 2 soli errori.
Abbiamo brevemente visto, in questo paragrafo, la grande potenza di
SVM, con tutte le opzioni di cui dispone, ma anche il suo più grande limite:
la necessità molto forte di un tuning particolareggiato degli iperparametri.
4.4.7
SVM per feature selection
Algoritmo
Abbiamo analizzato nel paragrafo 3.5 la PCA e il suo utilizzo per la
selezione di feature. Purtroppo, la PCA utilizza come input il dataset che
76
forniamo e rielabora le feature al fine di creare nuove variabili attraverso le
proiezioni, ottenute mediante gli autovettori: questo significa che è possibile
trovare un ranking di feature, ma riferito agli attributi nello spazio della PCA
(in cui poi saremmo costretti a lavorare), come mostrato anche negli esempi
del paragrafo 3.6. Non solo: la PCA è un metodo unsupervised, quindi
non tiene conto della classe di appartenenza dei pattern. Semplicemente,
seleziona gli autovettori che forniscono un contributo di energia maggiore al
dataset, ma tali componenti potrebbero non favorire la classificazione (ad
esempio), ma addirittura renderla più complessa.
Se ci occupiamo di problemi di classificazione, il nostro desiderio potrebbe essere quello, invece, di utilizzare una tecnica in grado di estrarre le
componenti, che ci permettono di classificare meglio le nostre osservazioni, e
di eliminare gli attributi “dannosi” per i nostri scopi. È possibile, quindi, utilizzare una SVM come algoritmo per effettuare la feature selection, cercando
di estrarre le componenti che più ci aiutano a creare un classificatore efficace.
La tecnica che andiamo a presentare venne proposta nel 2002 [11] e, dato un
set X con m feature, viene inizializzato creando due insiemi di indici, r e s,
rappresentanti rispettivamente gli attributi per i quali è già stato effettuato
ranking e le variabili ancora da ordinare. Al primo step, s contiene tutti gli
attributi del dataset originario. L’algoritmo procede, quindi, iterativamente
fino a quando s ≡ ∅, seguendo alcuni semplici passi:
1. si crea un subset Xi di X, il quale include solo le feature contenute nel
set di indici s;
2. si risolve la SVM, vincolata ad essere una SVM lineare, e viene
calcolato il vettore α;
3. per ogni feature, si calcolano i pesi del primale wj , j = 1, ..., s0 , dove
la norma–0 rappresenta la cardinalità dell’insieme (i.e., il numero di
elementi che compongono il set);
4. si calcola il coefficiente di ranking come cj = wj2 , in modo che l’importanza di una variabile sia calcolata sulla base del suo contributo nel
calcolo del margine;
5. si trova la feature j ∗ = arg min c;
77
6. si elimina la feature j ∗ dal set s e la si inserisce in testa al vettore r. In
questo modo, l’ultima variabile, eliminata nel processo iterativo, risulta
essere la prima (la più informativa) nel vettore r.
Ovviamente, è immediata la generalizzazione al caso in cui si vogliano eliminare più di una feature per step nel processo iterativo.
Non ci rimane che capire come possano essere calcolati i pesi wj2 per le
varie feature e il perchè del vincolo ad avere una SVM lineare. Ancora una
volta, come già per il bias, ci vengono in aiuto le KKT, per le quali otteniamo
che è possibile calcolare i pesi del primale come:
w=
l
yiαi φ(xi ),
(4.43)
i=1
dove φ(x) è una funzione tale per cui un kernel può essere definito come:
K(xi , xj ) = φ(xi ) · φ(xj ).
(4.44)
Avevamo detto che il kernel effettua un mapping non lineare ed implicito
dei dati, attraverso funzioni più o meno complesse; di fatto, un kernel è
un prodotto scalare tra due funzioni φ(·), le quali effettuano, in maniera
questa volta esplicita, tale mapping sui singoli dati. Se, nel caso lineare, vale
φ(x) = x, sfortunatamente per molti altri kernel (ad esempio, il gaussiano)
non è possibile calcolare le φ(·), ma solo K(xi , xj ). Ecco, quindi, il motivo
per il quale è necessario utilizzare una SVM lineare: almeno, conosciamo la
φ(·) ed è possibile procedere con il ranking.
L’estensione alla SVM non–lineare è comunque abbastanza semplice, anche se dispendiosa (in termini di risorse). Il coefficiente di ranking può essere
definito come:
cd =
1 1 αi αj qij −
αi αj qij ,
2 i j
2
(4.45)
i=d j=d
ovvero calcoliamo, in termini di peso nel margine e per ogni feature di s, l’influenza di ogni feature. Per il resto, l’algoritmo è identico a quello presentato
in precedenza.
78
Esempio di applicazione in WEKA
Lanciato WEKA explorer, dopo aver scelto il dataset weather ed esserci spostati nel tab per la selezione degli attributi, optiamo per l’algoritmo
“SVMAttributeEval” e analizziamone le opzioni:
• “attsToEliminatePErIteration” rappresenta il numero di attributi da
eliminare per ogni step;
• “complexityParameter” è il C di SVM lineare. Sfortunatamente, WEKA non dispone di un’estensione al caso non–lineare;
• “epsilonParameter” ha lo stesso significato visto nel caso di SVM;
• “filterType” permette di applicare filtri al training set;
• “percentThreshold” indica la percentuale di feature sotto la quale si
passa da un’eliminazione percentuale ad una costante delle feature.
Spieghiamoci meglio. In alternativa ad eliminare un certo numero (fissato) di feature per step, è possibile definire una percentuale sul totale
di attributi da estrarre; quando si scende sotto una certa soglia, si passa da un’eliminazione di variabili percentuale ad una costante per ogni
step. Settiamo a 0 questa opzione, in modo che essa venga disattivata;
• “percentToEliminatePerIteration” si riferisce alla percentuale di feature
da eliminare per step. Anche in questo caso, disattiviamo l’opzione,
settandola a 0;
• “toleranceParameter” è la tolleranza per SMO: 10−3 è normalmente un
valore accettabile.
Settato C = 1, lanciamo l’analisi e otteniamo un errore: tutte le variabili
devono essere quantitative o binarizzate. L’algoritmo non applica l’apposito
filtro in automatico: dobbiamo quindi spostarci nel tab di preprocessing e
applicare il filtro apposito per trasformare variabili nominali in binarie. Applicato il filtro, torniamo alla SVM per feature selection e lanciamo l’analisi.
Otteniamo la seguente “classifica”:
Ranked attributes:
6 6 windy
79
5
4
3
2
1
2
1
5
4
3
outlook=overcast
outlook=sunny
humidity
temperature
outlook=rainy
Verifichiamo ora la stabilità di tale ranking anche al variare di C. Settiamo, quindi, C = 100 e lanciamo nuovamente l’analisi. Otteniamo:
Ranked attributes:
6 5 humidity
5 2 outlook=overcast
4 4 temperature
3 6 windy
2 1 outlook=sunny
1 3 outlook=rainy
Notiamo che il ranking è stato profondamente modificato: in questo caso,
sarebbe quindi necessario un doppio lavoro di ricerca di iperparametro per la
classificazione e per la feature selection. Comunque, in molti casi reali, dove
i dataset sono caratterizzati da un maggior numero di pattern, le indicazioni
del ranking sono spesso più stabili.
4.5
4.5.1
Decision Trees
La nascita degli alberi di decisione
Abbiamo analizzato fino a questo punto molti metodi per la classificazione. Sfortunatamente, queste tecniche forniscono come output un modello,
al quale viene dato in pasto un nuovo pattern e che restituisce il target stimato dopo elaborazioni più o meno complesse sulle feature che compongono
l’istanza stessa. Nasce quindi il problema dell’interpretabilità del classificatore: avere un modello che classifichi stupendamente, ma che non sia in
grado di spiegarci (almeno in termini comprensibili) il fenomeno sottostante,
spesso non ci basta. Nei casi in cui abbiamo bisogno di regole interpretabili,
le quali portano poi alla classificazione di un pattern, dobbiamo ricorrere agli
alberi di decisione (decision trees, DT ).
80
Introdotti dall’australiano Quinlan [20], hanno avuto un ottimo successo
ed hanno subito diverse evoluzioni. La prima versione del software implementante i DT fu ID3, negli anni ’80: in ID3 si potevano utilizzare solo variabili
di tipo qualitativo, l’albero era solo binario (2 sotto–alberi per nodo al massimo) e l’algoritmo di apprendimento era piuttosto lento. Ciononostante, la
distribuzione gratuita del software1 (realizzato in C++) favorı̀ la diffusione
di ID3.
Agli inizi degli anni ’90 nacque poi C4.5: evoluzione di ID3 (in verità, di
una versione intermedia fra i due freeware, ovvero M5), era in grado di gestire
i missing e le variabili continue (solo con split di tipo binario, dopo sarà tutto
più chiaro). Inoltre, veniva introdotto un nuovo algoritmo di apprendimento,
più rapido, e la fase di pruning (che ci riserviamo di analizzare nei prossimi
paragrafi), che favorisce la generalizzazione del modello trovato. C4.5 ha
subito, nel corso degli anni, svariate migliorie, che hanno portato alla nascita
di una nuova versione del software per DT: Quinlan ha voluto mantenere il
nome C4.5, ma qualcuno ha ridefinito questa ulteriore release come C4.5+
o, più comunemente, C4.8 (in quanto si trattava dell’ottava release di C4.5).
Anche C4.5 (o C4.8 che dir vogliate) è disponibile free in rete sulla homepage
di Quinlan. Tra le novità in C4.8, la possibilità di gestire split multipli su
variabili continue e alcune nuove implementazioni per favorire l’esecuzione
parallela su più processori.
Ultima evoluzione, non più free ma commerciale, See5/C5.0: miglioramenti al codice hanno portato ad un algoritmo più veloce e che necessita di
meno memoria durante l’esecuzione. Non solo: nuovi algoritmi di pruning
migliorano le caratteristiche di generalizzazione in molti casi reali.
Come detto, il vantaggio dei DT è l’output dell’apprendimento: un modello sotto forma di regole if...then...else, dove gli if sono semplicemente
condizioni sul valore degli attributi. Un esempio di DT grafico è riportato in
Fig. 4.9. Spesso, l’interpretabilità va a scapito di prestazioni e, soprattutto,
generalizzazione nei casi reali. Tutto sarà più chiaro dopo aver analizzato in
breve l’algoritmo di learning.
1
http://www.rulequest.com/Personal/
81
Figura 4.9: Esempio di Decision Tree.
4.5.2
Apprendimento
Analizziamo l’algoritmo di apprendimento per C4.5 in versione originale, in quanto decisamente più semplice: solo alla fine di questo paragrafo
chiariremo le differenze e le novità di C4.8. L’apprendimento consiste di due
step:
• crezione dell’albero;
• pruning dell’albero.
Creazione dell’albero
Per capire bene l’apprendimento di un DT, dobbiamo partire col definire
alcune quantità. Al fine di comprendere meglio i parametri che andremo
a presentare, faremo degli esempi riferiti al dataset weather, presentato in
formato testuale in Tab. 4.2.
Definiamo come XG il dataset weather. Data una distribuzione di probabilità di una variabile, per esempio la distribuzione relativa di un attributo,
si definisce informatività di una variabile la quantità
I(P ) = −
i
82
pi log2 pi ,
(4.46)
Meteo
sunny
sunny
overcast
rainy
rainy
rainy
overcast
sunny
sunny
rainy
sunny
overcast
overcast
rainy
Temperatura
85
80
83
70
68
65
64
72
69
75
75
72
81
71
Umidità
85
90
86
96
80
70
65
95
70
80
70
90
75
91
Vento Giocare a golf?
FALSE
no
TRUE
no
FALSE
yes
FALSE
yes
FALSE
yes
TRUE
no
TRUE
yes
FALSE
no
FALSE
yes
FALSE
yes
TRUE
yes
TRUE
yes
FALSE
yes
TRUE
no
Tabella 4.2: Dataset weather.
equivalente all’entropia della variabile. L’informatività del nostro dataset, in
particolare, equivale all’informazione necessaria ad identificare una classe nel
nostro dataset. In termini matematici, vale
Inf o(X) = I(PX ) = −
k
pi log2 pi ,
(4.47)
i=1
con k che rappresenta il numero di classi. Ad esempio, nel dataset del golf
abbiamo 9 esempi appartenenti alla classe “yes” e 5 alla “no”. Pertanto,
abbiamo
5
9
5
9
log2
−
log2
≈ 0.94.
(4.48)
14
14 14
14
L’informatività è massima se le classi sono equidistribuite ed è minima se
una classe è assente.
Supponiamo per il momento di avere a disposizione solo variabili qualitative. Se dividiamo il nostro dataset X sulla base dei valori assunti da una
particolare variabile v, possiamo calcolare l’informatività del nostro dataset
relativamente alle partizioni che andiamo a calcolare. In pratica, vogliamo
calcolare l’informazione necessaria per identificare una classe in X, dopo che
Inf o (XG ) = −
83
un particolare valore di una variabile qualitativa è stato determinato. Ipotizzando che la variabile possa assumere n valori vi , i = 1, ..., n, possiamo
definire in breve Inf o(v, X):
Inf o(v, X) =
n
Xi 0
i=1
X0
· Inf o (Xi ) ,
(4.49)
nella quale Xi rappresentano i subset di X in cui un certo valore vi si mantiene
costante e la norma–0 ·0 è definita come la cardinalità di un dataset, ovvero
il numero di pattern che sono in esso contenuti. Nell’esempio del golf, per
l’attributo meteo possiamo calcolare l’informatività relativa:
5
Inf o(v, XG ) =
·I
14
2 3
4
3 2
5
4
,
, 0 + ·I
,
+ ·I
≈ 0.694. (4.50)
5 5
14
4
14
5 5
Infine, vogliamo trovare il guadagno, in termini di informatività, nell’introduzione della variabile v rispetto all’identificazione a priori di una classe.
Il guadagno viene definito come:
Gain(v, X) = Inf o(X) − Inf o(v, X).
(4.51)
Nel caso del meteo, otteniamo dalle Eqq. (4.48) e (4.50)
Gain(v, XG ) = 0.94 − 0.694 ≈ 0.246.
(4.52)
Si potrebbe mostrare che il guadagno della variabile vento è circa 0.094,
quindi l’introduzione nell’analisi di meteo porta ad un vantaggio maggiore
rispetto all’introduzione di vento. Il guadagno sarà esattamente la quantità
che guiderà la creazione del nostro albero.
Talvolta, in alternativa al guadagno, si utilizza il guadagno normalizzato,
definito come:
GainRatio(v, X) =
Gain(v, X)
,
SplitInf o(v, X)
(4.53)
dove la quantità SplitInf o(v, X) è definita sulla base dell’informatività dovuta allo splitting del dataset in subset nei quali una variabile qualitativa
mantiene valore costante:
SplitInf o(v, X) = I
X1 0 X2 0
Xn 0
,
, ...,
X0 X0
X0
84
.
(4.54)
Non ci rimane che generalizzare le quantità precedenti al caso di variabili
quantitative. Per quanto riguarda le feature discrete, se il numero di livelli
non è enorme si può supporre tali attributi come se fossero qualitativi ordinali. In caso contrario o per variabili continue, si segue questa procedura.
Si suppone che la variabile possa assumere solamente i valori presenti nel
dataset, ottenendo quindi un insieme vi , i = 1, ..., h. A questo punto, la
variabile continua dev’essere suddivisa (split) in due subset. Per trovare il
valore ottimo di split, si considerano tutti i vi e si calcolano tutti i guadagni
(eventualmente normalizzati) per i dataset splittati. Il punto di split che garantisce guadagno ottimo viene assunto come valore di riferimento, e il Gain
cosı̀ calcolato diviene il guadagno dell’attributo, che, a quel punto, diviene
una sorta di variabile qualitativa a tutti gli effetti.
L’algoritmo di apprendimento, a questo punto, procede con chiamate
ricorsive alla funzione di creazione dell’albero (ipotizziamo di utilizzare Gain,
ma anche con il valore normalizzato non cambia assolutamente nulla), routine
che definiamo createTree e il cui schema è il seguente:
1. se il set di dati passato in ingresso contiene solo dati appartenenti ad
una stessa classe, si inserisce una foglia corrispondente a tale classe e
si ritorna il controllo al chiamante;
2. se nel set di dati non sono più presenti feature, ma solo il target, si inserisce una foglia corrispondente al classe con frequenza assoluta maggiore
nel set e si ritorna il controllo al chiamante;
3. calcoliamo i Gain per tutti gli attributi;
4. sia v ∗ l’attributo con Gain massimo. Tale feature può assumere h
valori;
5. si creano gli h subset di dati contenenti ognuno un valore costante di
v ∗ . In essi, si elimina la feature v ∗ dal set;
6. per ognuno di essi, si crea un ramo dell’albero e si lancia la funzione
createTree.
Una volta conclusa l’operazione, abbiamo generato l’albero. La principale
differenza in C4.8 sta nella possibilità di non eliminare al passo 5 la variabile
dai subset se essa è continua: questo permette split multipli sui valori delle
85
variabili continue. Questa scelta è stata talvolta criticata, ma permette di
migliorare almeno parzialmente le performance del DT in casi in cui C4.5
andava profondamente in crisi, ovvero quando il numero di feature era molto
più alto del numero di pattern.
Notiamo che, se ci bloccassimo a questo punto, di fatto overfitteremmo
moltissimo il training set, cosa che non vogliamo. L’unica (e molto parziale)
generalizzazione è infatti contenuta nel passo 2, quando scegliamo la classe
di una foglia sulla base della classe più frequente. Il pruning viene proprio
utilizzato per favorire la generalizzazione dell’albero.
Pruning
Letteralmente, si traduce con potare: in effetti, rami dell’albero vengono
tagliati per favorire la generalizzazione del DT. Premesso che in letteratura
esistono innumerevoli tecniche per il pruning, una semplice strategia consiste
nel stimare l’errore nel caso di eliminazione di una parte dell’albero rispetto al
mantenimento della stessa. Se l’errore stimato è sotto una certa soglia, è considerato accettabile e il sotto–albero viene prunato; in caso contrario, viene
mantenuto. La stima dell’errore avviene utilizzando la formula di Laplace:
l−n+k−1
,
(4.55)
l+n
nella quale l è il numero di pattern contenuti nel subset riferito ad un nodo,
n è il numero di pattern del subset afferenti alla classe maggioritaria c e k è
il numero totale di classi. Se err è sotto la soglia, detta fattore di confidenza,
si sostituisce il sotto–albero con una foglia corrispondente alla classe c.
err =
4.5.3
Fase in avanti
Nella fase in avanti, si applicano semplicemente le regole, trovate durante
l’apprendimento, ad ogni nuovo pattern: l’uscita corrisponderà alla foglia
individuata nel tree mediante tali regole.
4.5.4
Estensione al caso multiclasse
Come già per NBC, MLP e 0–R, i DT sono nativamente multiclasse,
quindi non necessitano di estensioni.
86
4.5.5
Esempio di analisi in WEKA
Avviato WEKA explorer, consideriamo weather e, nel tab per la classificazione, selezioniamo i DT. In particolare, dovremo andare nella sottocategoria “trees”, nella quale C4.8 (WEKA utilizza questa versione) è identificato
come J4.8 (in quanto realizzato in Java e non in C++). Le opzioni a nostra
disposizione sono:
• “binarySplits” forza split di tipo binario anche su variabili qualitative. Permette, di fatto, il ritorno a ID3. A noi interessa C4.8, quindi
manterremo a false questa opzione;
• “confidenceFactor” è il fattore di confidenza per il pruning: più basso
è, più l’albero viene prunato. Valori tra 0.15 e 0.30 di solito sono i più
gettonati. Noi per ora settiamo 0.25;
• “debug” sono le solite stampe di debug;
• “minNumObj” permette di settare il numero minimo di istanze prima
di fissare una foglia nell’albero. Normalmente, si setta a 2;
• “numFolds” è il numero di fold per una tecnica di pruning efficace ma
complessa, la reduced error pruning, che non abbiamo analizzato;
• “reducedErrorPruning” è la citata tecnica. Settiamo a false;
• “saveInstanceData” permette di salvare i dati di training nella visualizzazione dell’albero;
• “seed” è il seed per l’algoritmo di random per la reduced error pruning;
• “subtreeRaising” permette all’algoritmo di pruning di valutare la modifica dei sotto–alberi al fine di migliorare le performance. Normalmente,
è settato a true;
• “unpruned” è utilizzato per disattivare il pruning (false);
• “useLaplace” permette di usare l’indice di Laplace per il pruning. Dato che spesso è un indice troppo conservativo, talvolta si disattiva
l’opzione. Anche noi, in effetti, la setteremo a false.
87
Lanciamo l’analisi e otteniamo ottimi risultati, paragonabili a quelli che
solo una SVM non lineare era riuscita a raggiungere. Anche scegliendo come
dataset iris, i risultati sono ottimi: solamente 3 errori e una Kappa molto
vicina a 1 (0.97). C’è inoltre da considerare che il DT ci fornisce anche
l’interpretabilità del modello, come mostrato in Fig. 4.10, quindi i parametri
di controllo sulla forma del sepalo e petalo del fiore: potrebbe esserci utile.
Per attivare la visualizzazione dell’albero, cliccate col tasto destro sul modello
nel menù “Result list” e selezionate la visualizzazione dell’albero.
Figura 4.10: Albero di decisione per il dataset iris.
88
Sappiamo, però, che uno dei principali difetti di C4.8 è la capacità di
generalizzazione. Pertanto, l’ultima prova consiste nell’utilizzo di 100 dati
di training e 50 di validation. Lasciando inalterati i settaggi, si ottengono
2 errori sul validation: un ottimo risultato. Per controllare se il pruning
ha influenza su questo risultato, settiamo a true l’opzione “unpruned” e
analizziamo i risultati: commettiamo nuovamente soli 2 errori, il che significa
che già il DT originale forniva un’ottima interpretazione del dataset.
89
Capitolo 5
Regressione
Terminata la nostra rassegna sugli algoritmi per la classificazione, passiamo al problema della regressione. Anche in questo caso, supporremo di avere
sempre a disposizione un dataset X, per il quale abbiamo definito un target
y ∈ di tipo numerico. L’obiettivo che ci prefiggiamo è trovare una relazione
fra feature e target per calcolare un output di tipo analogico efficace e con
un basso errore nella fase in avanti. Per verificare le prestazioni del nostro
modello, utilizzeremo i già analizzati RMSE e MAE ed introdurremo l’utilizzo del coefficiente di correlazione r (vedi paragrafo 3.3) tra le uscite reali
del nostro training o volidation set e quelle stimate dal modello: ricordiamo
che r ∈ [−1, 1] e r = 0 indica correlazione minima (e prestazioni pessime).
5.1
Zero Rules
Abbiamo analizzato nel paragrafo 4.1 il classificatore elementare 0–R.
Chiameremo, per evitare confusione, 0–RR il regressore Zero Rules.
5.1.1
Apprendimento
Analogamente a quanto visto per la classificazione, 0–RR utilizza come
uscita del modello la media dei target numerici del training set.
5.1.2
Fase in avanti
Qualunque sia l’ingresso al sistema, 0–RR restituisce come uscita stimata
la media dei target del training set.
90
5.1.3
Esempio di analisi in WEKA
È facile attendersi che la qualità di questo regressore sia davvero bassa; in
effetti, è proprio cosı̀. Lanciamo WEKA explorer e selezioniamo come dataset
per la regressione CPU (file cpu.arff ): tramite 6 attributi (caratteristiche di
alcune CPU), si cerca di stimarne le performance. Anche per la regressione
utilizzeremo il tab “classify” (WEKA non fa distinzione di sorta).
Per utilizzare 0–RR, selezioniamo l’algoritmo “ZeroR” (lo stesso usato nel
paragrafo 4.1.4) e lanciamo l’analisi. Il coefficiente di correlazione ottenuto è
pari a 0, il minimo possibile, e l’errore (sia in termine di MAE che di RMSE) è
molto alto. D’altra parte, il sistema stima sempre, a prescindere dal pattern
in ingresso, un’uscita ŷ ≈ 99.33. Se forziamo WEKA a stampare a video
anche le uscite del nostro training set, notiamo che ci sono anche valori come
−800, per i quali commettiamo un errore enorme. È quindi facile immaginare
che 0–RR (come il suo omologo 0–R) sia davvero poco usato.
5.2
Support Vector Regression
La Support Vector Regression (SVR) si basa sugli stessi principi della
SVM, con la quale condivide anche il principale autore [23]. L’idea di base
è quella di cercare una funzione ignota ŷ = f (x) che sia caratterizzata da
un errore basso (ma non nullo) rispetto ai dati di training. Esistono svariati
metodi per il calcolo dell’errore, ma noi analizzeremo solo uno dei più usati
(nonchè quello utilizzato da WEKA): la ε–insensitive loss function, per la
quale viene definita
|z|ε =
0
|z| − ε
se
se
|z| < ε
.
|z| ≥ ε
(5.1)
L’inconveniente di tale funzione di errore sta nel fatto che aggiungiamo un
nuovo iperparametro, ε, da settare in modo appropriato.
Il problema primale della SVR viene definito come [22]:
91
1
w2 + C
(ξi + ξi∗)
2
i=1
l
min
w ,b,ξ,ξ∗
(5.2)
yi − (w · x + b) ≤ ε + ξi
∀i ∈ [1, . . . , l]
(5.3)
(w · x + b) − yi ≤ ε + ξi∗
∀i ∈ [1, . . . , l]
(5.4)
ξi , ξi∗
≥ 0 ∀i ∈ [1, . . . , l]
(5.5)
ovvero in una forma sostanzialmente identica alla SVM a meno dell’introduzione di una doppia variabile di slack affinchè la stima dell’output ŷi possa
essere sia minore che maggiore rispetto all’output reale yi. In Fig. 5.1, presentiamo un esempio grafico che dovrebbe meglio chiarire il significato del
doppio slack.
Figura 5.1: Rappresentazione grafica della ε–insensitive loss function.
Il problema duale di SVR può essere calcolato in maniera analoga a quanto visto per la SVM utilizzando il metodo dei moltiplicatori di Lagrange,
ottenendo:
min
α,α∗
l l
∗
∗
i=1
j=1 (αi − αi ) αj − αj K(xi , xj )+
−ε li=1 (αi + αi∗ ) + li=1 yi (αi − αi∗ )
1
2
0 ≤ αi , αi∗ ≤ C ∀i ∈ [1, . . . , l]
l
(αi − αi∗ ) = 0.
(5.6)
(5.7)
(5.8)
i=1
5.2.1
Apprendimento
Tramite passaggi non troppo complessi, per i quali rimandiamo a [22],
è possibile ricondurre il problema (5.6) alla formulazione duale (4.34) della
92
SVM, pertanto risolvibile usando SMO. Ed è infatti proprio questo algoritmo che utilizzeremo per trovare la soluzione ottima, che nel caso di SVR
comprende sia α che α∗ , oltre, ovviamente, al bias, calcolabile sfruttando le
KKT.
5.2.2
Fase in avanti
Anche la fase in avanti della SVR ricorda molto da vicino la funzione
feedforward di SVM. Nella fattispecie, vale:
ŷ = f (x) =
l
(αi − αi∗ ) K (x, xi ) + b.
(5.9)
i=1
5.2.3
Esempio di analisi in WEKA
Lanciamo WEKA explorer, selezionando CPU come dataset. Nel tab di
classificazione, selezioniamo “SMOreg” dalla sottocategoria “functions” per
selezionare la SVR. Le opzioni sono sostanzialmente le stesse della SMO per
la classificazione, per le quali rimandiamo al paragrafo 4.4.6. Unico cambiamento, l’aggiunta dell’opzione “epsilon” per la tolleranza dell’omonima
ε–insensitive loss function: setteremo ε = 0.001.
Partiamo con un kernel lineare e C = 1. Lanciamo l’analisi e otteniamo
risultati di sicuro buoni, ma non esaltanti: l’errore presenta un miglioramento
in termini assoluti pari a circa il 78% rispetto a 0–RR, e il coefficiente di
correlazione è oltre 0.9. Con un kernel gaussiano possiamo fare di meglio?
Settiamo γ = 1 e otteniamo un errore veramente piccolo (miglioramento in
termini assoluti del 98% rispetto a 0–RR) e un coefficiente di correlazione
sostanzialmente equivalente a 1. Portiamo γ = 100: otteniamo addirittura
r = 1 e un errore quasi nullo. Davvero un’ottima performance.
5.3
5.3.1
Regression Trees
Apprendimento
I Regression Trees (RT) ricordano non solo nel nome i DT: infatti, l’algoritmo di apprendimento è assolutamente identico a quanto analizzato nel
paragrafo 4.5.2. L’unica differenza consta nello stabilire il valore di una foglia:
93
se, nel caso dei DT, si sceglieva la classe maggioritaria, nei RT si considera
la media dei target del subset “sopravvissuto” ai precedenti split.
5.3.2
Fase in avanti
Anche per la fase feedforward, rimandiamo alla discussione sui DT e, in
particolare, al paragrafo 4.5.3.
Alcune considerazioni vanno fatte, invece, sulle performance dei RT, spesso insufficienti in molti casi reali. Anche lo stesso Quinlan ha portato avanti
i RT parallelamente ai DT a partire dall’algoritmo M5 (sviluppato prima di
C4.5) fino a C4.5 stesso. Da C4.8 in poi, date le scarse performance degli RT
(specie in dataset caratterizzati da un alto rapporto fra numero di pattern e
numero di attributi), essi non sono stati più inclusi nei pacchetti distribuiti
in rete.
5.3.3
Esempio di analisi in WEKA
Anche WEKA risente dell’abbandono nello sviluppo dei RT in C4.8: il
già citato algoritmo J4.8 non contempla la possibilità di creare un albero per
regressione. A causa di ciò, utilizzeremo l’algoritmo più vecchio (M5) [19],
reso (parzialmente) più performante da alcune migliorie in stile C4.8 [24]: tra
queste, l’utilizzo di un problema di regressione lineare sulle foglie al posto
della media. Rimandiamo agli articoli citati per coloro che volessero maggiori
dettagli: le differenze nel learning rispetto a C4.5/C4.8 sono minime.
Sono minime anche le differenze in WEKA rispetto alle opzioni per J4.8:
selezionato l’algoritmo “M5P” (dove ‘P’ indica Plus, ovvero dotato delle modifiche apportate in [24]), i parametri da settare sono quelli analizzati nel
paragrafo 4.5.5; unica aggiunta, il parametro che regola l’implementazione di
un RT “buildRegressionTree” (per noi, sarà true). Merita una nota aggiuntiva il parametro “minNumIstances”: se nel caso dei DT avevamo settato
tale parametro a 2, ora conviene aumentare il numero minimo di istanze necessarie per consentire un ulteriore split. Se, infatti, nel calcolo del valore di
una foglia dovessero rimanere troppi pochi pattern, il valore mediato potrebbe essere di poco significato. Un buon valore può essere considerato 4; con
tanti pattern, meglio aumentare ulteriormente tale limite (ma non troppo,
altrimenti potremmo addirittura non riuscire a creare l’albero). L’opzione
“useUnsmoothed” equivale alla “useLaplace” dei DT.
94
Lanciamo l’analisi su CPU e otteniamo un errore piuttosto alto: otteniamo un miglioramento pari circa al solo 60% rispetto a 0–RR e il coefficiente
di correlazione non è alto (circa 0.8).
SVR sembra il miglior algoritmo per la regressione: lo sarà anche su un
validation set, separato dal training set? Trascurando 0–RR, di sicuro pessimo, utilizziamo il 67% dei dati per il training e il restante come validation.
Con RT, otteniamo sul validation i tre seguenti valori:
• r = 0.85;
• errore MAE relativo a 0–RR: 44.21%;
• errore RMSE relativo a 0–RR: 54.89%.
Lanciamo SVR con kernel gaussiano e i parametri identificati nel paragrafo 5.2.3. I valori ottenuti sono decisamente migliori:
• r = 0.97;
• errore MAE relativo a 0–RR: 18.08%;
• errore RMSE relativo a 0–RR: 22.86%.
95
Capitolo 6
Clustering
Altro problema interessante da affrontare in ottica BI è il clustering: esso
consiste nel raggruppamento di elementi omogenei in un insieme di dati. Le
tecniche di clustering si basano sul concetto di distanza, che risulta quindi
centrale nell’analisi: elementi “vicini” (secondo una certa metrica) sono da
considerarsi omogenei e vanno inseriti nello stesso cluster; pattern eterogenei
saranno “distanti” ed inclusi in differenti insiemi.
Le tecniche di clustering vengono utilizzate spesso quando si hanno a
disposizione dati eterogenei e si è alla ricerca di elementi anomali: un caso
tipico riguarda le compagnie telefoniche, le quali utilizzano le tecniche di
clustering per cercare di individuare in anticipo gli utenti che diventeranno
morosi. Essi, infatti, tendono ad avere un comportamento diverso rispetto
alla normale utenza e le tecniche di clustering riescono sovente ad individuarli
o almeno a definire un cluster, nel quale vengono concentrati tutti gli utenti
che hanno un’elevata probabilità di diventare morosi.
Per il clustering, in generale, non avremo a disposizione un target, ma
semplicemente un dataset X, composto da un certo numero di feature. Spesso
non si conosce nemmeno il numero di cluster k a priori: in questo caso,
k diviene una sorta di iperparametro, il cui valore ottimo va ricercato per
tentativi.
6.1
k–Means
Per quanto riguarda il clustering, analizzeremo solo un algoritmo: il k–
means. È un algoritmo piuttosto semplice, ma spesso efficace. Negli ultimi
96
anni sono stati sviluppati anche algoritmi più complessi, ma un po’ per motivi
di tempo e un po’ per gli scarsi miglioramenti conseguiti tralasceremo tali
metodi.
6.1.1
Apprendimento
L’algoritmo per l’apprendimento è di tipo iterativo e necessita di due
ingressi (oltre al training set X, ovviamente):
• una metrica di distanza tra pattern: spesso viene usata la distanza euclidea x1 − x2 22 . Ovviamente, usando tale distanza i cluster avranno
forma di (iper)sfere, il cui centro viene detto centroide;
• il numero di cluster k < l (se non disponibile, bisogna procedere per
tentativi), dove l è il numero di pattern di training.
La funzione che intendiamo minimizzare è:
CKM
k
xj − μj 2 ,
= min
2
μ1 ,...,μk
i=1 xj ∈Sj
(6.1)
dove μj , j = 1, ..., k, indicano i k centroidi e Sj sono i k cluster. In generale,
il centroide non è un punto del training set, ma viene individuato mediando
la posizione dei punti appartenenti al cluster; nel caso in cui non si usi la
media delle coordinate dei punti del cluster, bensı̀ la mediana, si parla di
k–medoids, di cui noi non ci occuperemo.
L’algoritmo viene inizializzato scegliendo k centroidi randomicamente tra
i punti del training set. A questo punto, l’apprendimento procede seguendo
questi step:
1. si calcolano i cluster, assegnando ogni pattern al cluster il cui centroide
dista meno;
2. si modificano i centroidi, ricalcolandoli sulla base dei nuovi punti appartenenti al cluster;
3. se i centroidi non sono stati modificati (o hanno subito un cambiamento
inferiore ad una certa soglia), l’algoritmo termina; altrimenti si procede
dal punto 1.
97
Ovviamente, la qualità del risultato dipende anche dall’inizializzazione randomica dei centroidi: per questo motivo, è spesso preferibile lanciare diverse
istanze di k–means, partendo da centroidi differenti. Alla fine, si opta per la
configurazione a CKM minimo.
6.1.2
Fase in avanti
La fase feedforward del k–means consiste, per un nuovo pattern x, nel
calcolarne la distanza dai centroidi e nell’attribuirlo al cluster il cui centroide
dista meno.
6.1.3
Esempio di analisi in WEKA
In WEKA non esistono dataset creati ad hoc per il clustering; d’altra
parte, è possibile utilizzare alcuni dataset, originalmente creati per la classificazione, e vedere come si comporta il k–means in questi casi. Tra l’altro,
per questi dataset conosciamo il numero di cluster, essendo coincidente con
il numero di classi.
Iniziamo con il già noto iris e selezioniamo il tab “Cluster”; tra i metodi disponibili, optiamo per il “SimpleKMeans”, le cui opzioni riguardano
semplicemente il numero di cluster (per iris, k = 3) e il seed per l’algoritmo di inizializzazione random (inizialmente, lasciamo 10). Essendo il nostro
dataset iris nato per algoritmi di classificazione, selezioniamo tra i “Cluster
mode” l’opzione “Classes to cluster evaluation”, che ci offre un termine di
paragone diretto con la classificazione nell’output dei risultati.
L’output del k–means per la nostra analisi è il seguente:
Number of iterations: 6
Within cluster sum of squared errors: 6.99811
Cluster centroids:
Cluster 0
Mean/Mode:
Std Devs:
Cluster 1
Mean/Mode:
5.8885 2.7377 4.3967 1.418
0.4487 0.2934 0.5269 0.2723
5.006
3.418
1.464
98
0.244
Std Devs:
Cluster 2
Mean/Mode:
Std Devs:
0.3525 0.381
0.1735 0.1072
6.8462 3.0821 5.7026 2.0795
0.5025 0.2799 0.5194 0.2811
ovvero ci viene presentato il numero di iterazioni totale, l’errore quadratico
intra–cluster (di fatto, il costo CKM ) e i centroidi dei cluster, sotto forma di
media (o moda nel caso di variabili qualitative) e varianza (usata più che altro
come indice di stabilità del centroide). Segue, quindi, il numero di pattern
del training set assegnato ad ogni cluster e una sorta di Confusion Matrix
riferita ai cluster. Conclude l’elenco dei risultati il numero e la percentuale
di assegnazioni errate ai cluster (misurate sulla base dell’appartenenza alle
varie classi). Nel caso di iris abbiamo l’11.3% di errore (valore alto, se riferito
a quelli ottenuti nel capitolo 4).
Proviamo a modificare il seed e settiamolo a 356 (un valore a caso): otteniamo gli stessi risultati dell’esecuzione precedente. Si possono provare molti
valori di seed e vedere se la percentuale precedente migliora. Un’ultima nota:
dall’analisi della pseudo–Confusion Matrix, si evince che la classe 0 (“Iris–
setosa”) viene sempre clusterizzata in modo perfetto e quindi, probabilmente,
è facilmente distinguibile dalle altre due classi.
In fase di introduzione a questo capitolo, abbiamo detto che spesso il clustering è utilizzato per trovare clienti morosi: in WEKA, è incluso il dataset
labor, per classificazione binaria, in cui, sulla base del profilo di alcuni lavoratori, si prova a stimare se essi siano dei buoni lavoratori o meno. Proviamo
ad applicare il k–means, con k = 2 e seed pari a 10: sbagliamo nel 23% circa
dei casi. Non solo, tali errori sono particolarmente gravi, in quanto quasi
per intero si riferiscono a cattivi lavoratori che vengono, invece, caratterizzati nella classe “good”. Proviamo a cambiare seed, settandolo a 1000: la
situazione peggiora (passiamo quasi al 40% di errore), e questa volta siamo
troppo “cattivi” (consideriamo troppi lavoratori come “bad”). Causa di queste scarse performance potrebbe essere la presenza di molti missing tra i dati
di labor.
99
Capitolo 7
Association rules
Uno dei primi esempi che abbiamo presentato in queste dispense riguardava la catena di supermercati, in cui volevamo cercare possibili associazioni
fra prodotti (o fra prodotto e acquirente) per regolamentare la disposizione
delle merci nei nostri supermercati. In questi casi, e in moltissimi altri nella
vita di tutti i giorni prima ancora che nel mondo della BI, è necessario trovare regole che leghino fra loro alcune variabili; in termini di Data Mining,
dobbiamo trovare eventuali relazioni causali tra feature che descrivono una
qualche entità.
Gli algoritmi per trovare association rules ricevono, in ingresso, un dataset X, composto da l pattern e m feature, senza alcun target: l’obiettivo è
trovare relazioni del tipo if x1 = 10 ∨ x6 > 33 then x3 = false, ovvero relazioni
di causalità, similmente a quanto visto per i DT. In questo caso, a differenza
degli alberi, però, il nostro obiettivo non è trovare una sorta di “percorso
ottimo” che, dagli ingressi, attraverso un certo numero di regole ci porti verso
le uscite, bensı̀ vogliamo trovare un qualsiasi legame che colleghi in qualche
modo due o più feature del nostro dataset. In termini meno informali, diremo
che, mentre i DT erano un metodo supervised (sapevamo cosa volevamo
trovare, ovvero il target), gli algoritmi di association rules sono unsupervised,
in quanto partiamo dal principio di non conoscere nulla del nostro dataset e di
voler cercare di ottenere informazioni attraverso l’applicazione di un qualche
algoritmo. Non solo: nel caso delle association rules l’algoritmo si conclude,
di fatto, con la fase di apprendimento, in quanto una vera fase in avanti non
esiste. Infatti, ciò che ci interessa non è trovare un modello da applicare a
run–time, ma solo identificare relazioni all’interno di X. Per questo motivo,
100
non definiremo per l’algoritmo che analizzeremo alcun indice di qualità, in
quanto non definibile di per sè.
Esistono diversi algoritmi per trovare le regole di associazioni tra feature:
noi analizzeremo uno dei più usati, Apriori. A prescindere dall’algoritmo che
si vuole usare, normalmente le implementazioni di association rules prevedono di trattare solo feature di tipo qualitativo: qualora avessimo variabili
quantitative, dovremo procedere ad una discretizzazione ad hoc, magari utilizzando le tecniche già brevemente analizzate per i DT (si veda paragrafo
4.5.2).
7.1
Apriori
Apriori [1] è uno degli algoritmi in assoluto più utilizzati e si basa su
alcune quantità, piuttosto semplici da calcolare. Le regole che verranno trovate saranno nella forma if A then B, rappresentate alternativamente come
A → B, dove A è detto antecedente o body mentre B è detto conseguente o
head. Al fine di chiarire meglio alcuni concetti, utilizzeremo come esempio il
dataset weather : dato che esso contiene, nella sua forma originaria, alcune
variabili quantitative, utilizzeremo la versione discretizzata di queste ultime.
Per semplicità, proponiamo il dataset in Tab. 7.1.
7.1.1
Apprendimento
Partiamo con alcune definizioni. Viene detto supporto la percentuale di
pattern nel dataset per le quali una determinata condizione è verificata:
lA
,
(7.1)
l
dove lA rappresenta il numero di pattern in cui la condizione A è soddisfatta
e l il numero totale di pattern nel dataset. Ad esempio, nel dataset di Tab.
7.1, abbiamo:
support(A) =
5
≈ 0.36.
(7.2)
14
Talvolta, il supporto viene inteso in termini assoluti e non relativi: in tal
caso, non si divide per l. Ad esempio, per il caso della condizione meteo =
rainy, avremmo un supporto pari a 5.
support(meteo = rainy) =
101
Meteo
sunny
sunny
overcast
rainy
rainy
rainy
overcast
sunny
sunny
rainy
sunny
overcast
overcast
rainy
Temperatura
hot
hot
hot
mild
cold
cold
cold
mild
cold
mild
mild
mild
hot
mild
Umidità
high
high
high
high
normal
normal
normal
high
normal
normal
normal
high
normal
high
Vento Giocare a golf?
FALSE
no
TRUE
no
FALSE
yes
FALSE
yes
FALSE
yes
TRUE
no
TRUE
yes
FALSE
no
FALSE
yes
FALSE
yes
TRUE
yes
TRUE
yes
FALSE
yes
TRUE
no
Tabella 7.1: Dataset weather in forma discretizzata, con variabili solo di tipo
qualitativo.
102
Viene definita confidenza di una regola A → B il rapporto fra il supporto
della regola e il supporto dell’antecedente A:
conf idence(A → B) =
support(A → B)
lA→B
=
.
support(A)
lA
(7.3)
Consideriamo la regola if (meteo = sunny) then play = yes e calcoliamone
la confidenza. Partiamo col definirne il supporto: è immediato calcolare
che support(meteo = rainy → play = yes) = 3/14 ≈ 0.21. Abbiamo già
calcolato che il supporto dell’antecedente è circa uguale a 0.36. Pertanto, la
confidenza è:
3
= 0.6.
(7.4)
5
Infine, definiamo il lift di una regola A → B come il rapporto fra la
confidenza della regola e il supporto del conseguente, ovvero:
conf idence(meteo = rainy → play = yes) =
lif t(A → B) =
support(A → B)
conf idence(A → B)
=
.
support(B)
support(A)support(B)
(7.5)
Ad esempio, si ottiene facilmente che lif t(meteo = rainy → play = yes) ≈
0.6
≈ 0.94. Si potrebbero definire altre quantità, talvolta utilizzate (leverage
0.64
e convinction su tutte), ma sono piuttosto complesse ed esulano dalla nostra
analisi. Ci interessa, invece, analizzare una misura, detta di significanza
(significance, interestingness): il chi–quadro (χ2 ), spesso utilizzata per il
ranking delle regole di associazione e definita come:
χ2 (A → B) =
(support(A → B) − support(A)support(B))2
.
support(A)support(B)
(7.6)
Definite le principali quantità che dovremo considerare nella creazione
delle regole, diamo un’occhiata all’algoritmo. Apriori è un metodo iterativo,
che procede creando cosiddetti itemset, ovvero insiemi di regole per le quali alcune condizioni sono verificate. Tipicamente, si pongono condizioni sul
supporto e sulla confidenza o, in alternativa a quest’ultima, sul lift. Un’ulteriore selezione può essere fatta sul livello di significanza di una regola, usando
χ2 . Supponiamo di aver definito una soglia di supporto minimo suppm e una
soglia di confidenza minima confm . Analizziamo i passi di Apriori.
103
Al primo passo, vengono considerati i supporti di tutte le possibili combinazioni di variabili presenti in X. Le combinazioni il cui supporto supera
suppm entrano a far parte dell’itemset 1.
Al passo successivo, si parte da tutte le relazioni dell’itemset 1, si trovano tutte le loro possibili combinazioni e, per ognuna di esse, si calcolano
i supporti: entreranno a far parte dell’itemset 2 tutte le combinazioni che
superano la soglia di supporto.
Si procede iterativamente a creare itemset, fino a quando non si finiscono
le possibili combinazioni e/o nessuna nuova combinazione ha un supporto
maggiore rispetto alla soglia. A questo punto, si trovano le prime regole, nelle
quali la relazione aggiunta nell’ultimo itemset risulta essere l’head mentre le
precedenti costituiscono il body. Ad esempio, se nell’ultimo itemset troviamo
una relazione del tipo:
humidity=normal windy=FALSE play=yes
play=yes costituirà l’head e l’AND delle due relazioni precedenti (humidity=
normal e windy=FALSE) sarà il body. Una volta terminate queste relazioni,
si continua a creare regole utilizzando le ultime due istanze come head (es.,
windy=FALSE e play=yes) e le restanti come body (es., humidity=normal).
Il passo successivo consiste nel ripetere queste operazioni per tutti gli itemset
precedenti, escluso l’itemset 1 (per il quale avevamo ancora solo una relazione). Alla fine, per ogni regola viene calcolata la confidenza e, se necessario, la
significanza: vengono prese in considerazione le sole regole aventi confidenza
maggiore di confm (e, se definita, significanza maggiore di una soglia χ2m ).
7.1.2
Esempio di analisi in WEKA (I)
Abbiamo detto che spesso, per analisi di tipo association rules, necessitiamo di dataset composti da variabili solo di tipo qualitativo. È questo
il caso di WEKA. Se vogliamo, quindi, cominciare le nostre analisi con un
dataset semplice quale weather, dobbiamo utilizzarne la versione composta
da sole variabili qualitative, cioè weather.nominal.
Nel tab “Associate”, selezioniamo il metodo “Apriori”, le cui opzioni
sono:
• “delta” rappresenta il decremento iterativo del supporto dal suo valore
massimo al suo valore minimo (settiamo 0.05);
104
• “lowerBoundMinSupport” è il minimo supporto necessario affinchè un
insieme di relazioni venga ammesso in un itemset (0.3 è un buon valore);
• “metricType” definisce la metrica con cui vengono definite le regole
ammesse a far parte del set finale (useremo la confidenza);
• “minMetric” è il valore minimo della metrica necessario affinchè la
regola venga inclusa nel set finale (settiamo 0.9);
• “numRules” è il numero massimo di regole richieste (ad esempio, 10
regole);
• “outputItemSets” stampa a video i vari itemset (è utile settarlo a true
per analizzare come funziona l’algoritmo);
• “removeAllMissingColumns” rimuove feature in cui sono presenti missing (false);
• “significanceLevel” è il livello di significanza minimo χ2 (disattiviamo
l’opzione settando -1);
• “upperBoundMinSupport” è il massimo supporto necessario (1);
• “verbose” produce alcune stampe di debug.
Lanciamo l’analisi e otteniamo le seguenti regole:
1. humidity=normal windy=FALSE 4 ==> play=yes 4
conf:(1)
2. temperature=cool 4 ==> humidity=normal 4
conf:(1)
3. outlook=overcast 4 ==> play=yes 4
conf:(1)
Avevamo richiesto 10 regole, ma solo 3 riescono a soddisfare i vincoli su
supporto e confidenza. Se abbassiamo il limite minimo per il supporto a 0.2,
otteniamo:
1.
2.
3.
4.
5.
6.
humidity=normal windy=FALSE 4 ==> play=yes 4
conf:(1)
temperature=cool 4 ==> humidity=normal 4
conf:(1)
outlook=overcast 4 ==> play=yes 4
conf:(1)
temperature=cool play=yes 3 ==> humidity=normal 3 conf:(1)
outlook=rainy windy=FALSE 3 ==> play=yes 3
conf:(1)
outlook=rainy play=yes 3 ==> windy=FALSE 3
conf:(1)
105
7. outlook=sunny humidity=high 3 ==> play=no 3
8. outlook=sunny play=no 3 ==> humidity=high 3
conf:(1)
conf:(1)
ovvero qualche regola in più, ma a minore supporto (solo 3 esempi in tutto
il dataset).
7.1.3
Esempio di analisi in WEKA (II)
E se avessimo solamente a disposizione un dataset con variabili quantitative? Perchè non possiamo trovare relazioni, ad esempio, in iris? Per poter
utilizzare anche questi dataset, è necessario applicare un filtro ai dati stessi.
Nel tab di preprocessing dei dati, selezioniamo iris e optiamo per il filtro
“Discretize” nelle sottocategorie “unsupervised” e “attribute”. Le opzioni
del filtro sono:
• “attributeIndices” rappresenta l’elenco degli indici degli attributi numerici da discretizzare (“last-first” indica che vogliamo discretizzare
tutti gli attributi, se numerici);
• “bins” rappresenta il numero di intervalli (per esempio, potremmo
settarlo a 5);
• “desiredWeightOfIstancesPerInterval” permette di settare un peso per
ogni pattern in ogni intervallo (disattiveremo l’opzione, settando -1);
• “findNumBins” ricerca automaticamente il numero di intervalli in cui
splittare una feature (tra 1 e il valore di “bins”). Settiamo true;
• “invertSelection” discretizza solo le variabili non selezionate nella prima
opzione (false);
• “makeBinary” binarizza le feature dopo averle discretizzate (false);
• “useEqualFrequency” trova gli intervalli sulla base di indici di frequenza
e non in intervalli di uguale dimensione (false).
Applichiamo il filtro e, quindi, lanciamo l’analisi di Apriori, richiedendo
un supporto minimo del 30%. Troviamo le seguenti regole:
106
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
petallength=’(-inf-2.18]’ 50 ==> class=Iris-setosa 50
conf:(1)
class=Iris-setosa 50 ==> petallength=’(-inf-2.18]’ 50
conf:(1)
petalwidth=’(-inf-0.58]’ 49 ==> petallength=’(-inf-2.18]’ class=Iris-setosa
petallength=’(-inf-2.18]’ petalwidth=’(-inf-0.58]’ 49 ==> class=Iris-setosa
petalwidth=’(-inf-0.58]’ class=Iris-setosa 49 ==> petallength=’(-inf-2.18]’
petalwidth=’(-inf-0.58]’ 49 ==> class=Iris-setosa 49
conf:(1)
petalwidth=’(-inf-0.58]’ 49 ==> petallength=’(-inf-2.18]’ 49
conf:(1)
petallength=’(-inf-2.18]’ 50 ==> petalwidth=’(-inf-0.58]’ class=Iris-setosa
class=Iris-setosa 50 ==> petallength=’(-inf-2.18]’ petalwidth=’(-inf-0.58]’
petallength=’(-inf-2.18]’ class=Iris-setosa 50 ==> petalwidth=’(-inf-0.58]’
49 conf:(1)
49 conf:(1)
49 conf:(1)
49 conf:(0.98)
49 conf:(0.98)
49 conf:(0.98)
Siamo quindi in grado di trovare 10 regole anche su variabili quantitative: la
prima regola potrebbe infatti essere scritta anche come If petal length ≤ 2.18
then class = Iris–setosa.
Una nota conclusiva: avevamo notato già nel capitolo sul clustering al
paragrafo 6.1.3 che, in iris, la classe Iris–setosa era particolarmente facile
da riconoscere: in effetti, Apriori ci spiega perchè. Infatti, è sufficiente controllare la lunghezza del petalo: se è sotto una certa cifra (2.18), abbiamo la
certezza (confidenza pari al 100%) che si tratti di questo tipo di fiore.
107
Capitolo 8
Valutazione comparativa di
algoritmi di Data Mining
8.1
Metodi (pratici) per la comparazione fra
algoritmi
Premettiamo subito che in questo capitolo non affronteremo davvero nei
particolari la comparazione fra algoritmi, che sarebbe davvero un argomento difficile ed impegnativo, nè analizzeremo tutte le tecniche disponibili in
letteratura. Quello che intendiamo fare, invece, è proporre alcune semplici metodologie, che possono essere usate anche in WEKA e permettono di
ottenere velocemente semplici parametri di valutazione di metodi statistici.
8.1.1
Training set (TS)
Il primo metodo, il più semplice, prevede la valutazione delle performance
di un algoritmo di DM sulla base del numero di errori che il modello commette
sul training set. È la tecnica che abbiamo utilizzato nelle nostre prime analisi
in WEKA. Il problema sta nel fatto che valutare le performance di un metodo
sugli stessi dati su cui è stato creato il modello può portare ad overfitting:
per questo motivo, questa tecnica è davvero poco utilizzata.
108
8.1.2
Validation set (VS)
Molto più appropriato per i nostri scopi è utilizzare un validation set
separato dal training set, che possiamo fornire in un file separato o ottenere
splittando in training e validation il dataset che abbiamo a disposizione.
Selezioneremo alla fine il modello che, istruito sul training set, meglio si
comporta sul validation set.
8.1.3
K–Fold Cross Validation (KCV)
La tecnica di valutazione forse più usata è, però, la k–Fold Cross Validation (KCV ): essa prevede che il dataset che abbiamo a disposizione venga
diviso in k subset, detti fold, di uguali dimensioni (nel caso in cui il numero di
pattern l non sia esattamente divisibile per k, normalmente, si duplicano dei
dati presenti nel dataset originario). A turno, k − 1 fold vengono usate per
l’apprendimento e la restante fold come validation: ad esempio, ipotizzando
10 fold, al primo passo useremo le fold dalla 1 alla 9 per il training e la 10
come validation; al secondo step, dalla 1 alla 8 e la 10 come training e la 9
come validation, e cosı̀ via. Su ogni fold di validation, è possibile calcolare il
numero di errori ei , i = 1, ..., k. Alla fine, il parametro per il confronto tra
metodi sarà pari a:
k
i=1 ei
.
(8.1)
l
Il vantaggio della KCV è che, se abbiamo un singolo dataset (quindi,
senza validation separato), non sprechiamo dati per il training, dato che a
turno tutti i pattern vengono usati per l’apprendimento; non solo, abbiamo
anche un validation set molto grande, essendo alla fine composto anch’esso,
di fatto, da tutte le istanze del dataset. Lo svantaggio consiste nel dover
ripetere k volte l’apprendimento: questo significa lunghi tempi di attesa nel
caso di dataset con molti pattern di training.
Un paio di note conclusive. Spesso, prima di applicare la KCV è necessario un rimescolamento casuale dei dati del dataset: questo per evitare che
una fold per il training sia costituita da soli dati di una classe, ad esempio.
Fissare k potrebbe essere considerato come una ricerca di iperparametro: in
verità, la pratica ha ampiamente dimostrato che k = 5 e k = 10 sono valori
ottimi da utilizzare.
e=
109
Metodo
Errore TS
NBC
18.33%
MLP
2.33%
SVM lin
3.27%
SVM gauss
1.00%
1.00%
DT
Errore test
22.96%
4.81%
5.31%
2.84%
3.83%
Tabella 8.1: Risultati per il metodo training set (TS): in grassetto, le migliori
percentuali ottenute.
8.2
Analisi in WEKA explorer
Per le nostre prove, considereremo un dataset finora mai introdotto, segment, rappresentante porzioni di immagini da classificare in 7 classi sulla base
del materiale in esse rappresentato (erba, cemento,...). Il dataset è composto
da ben 1500 pattern, ma, cosa a noi ancor più gradita, è incluso un test set:
ciò significa che partiremo a confrontare metodi statistici per la classificazione (NBC, MLP, SVM lineare, SVM gaussiana, DT), ne sceglieremo uno
per ogni tecnica di confronto (TS, VS, KCV) e verificheremo poi sul test set
quale si comportava meglio. In particolare, per SVM useremo C = 100 e, nel
caso di SVM gaussiana, γ = 1.
8.2.1
Metodo TS
Carichiamo il dataset di training in WEKA explorer. Partiamo con il
TS. I risultati sono presentati in Tab. 8.1: i metodi migliori appaiono essere
la SVM gaussiana e gli alberi. Per valutare l’errore sul file di test, utilizziamo
“Supplied test set” nel menù “Test options” e selezioniamo il file di test per
segment. Notiamo che le previsioni di stima sul training set sono effettivamente verificate: i metodi che meglio si comportano in termini di errore sul
training set sono quelli che meglio vanno anche sul test set. In questo caso,
quindi, presumiamo che il training set sia un buon campione del problema
che stiamo analizzando.
Ciononostante, notiamo due cose:
• il metodo TS stima come ugualmente performanti SVM gaussiana e
DT, anche se, in verità, sul test set vi è poi una differenza pari quasi
110
Metodo
Errore VS Errore test
NBC
19.87%
22.96%
MLP
4.40%
4.81%
SVM lin
4.93%
5.31%
SVM gauss
3.47%
2.84%
5.60%
3.83%
DT
Tabella 8.2: Risultati per il metodo validation set (VS): in grassetto, le
migliori percentuali ottenute.
all’1%. D’altra parte, era lecito attenderselo: sappiamo che i DT, al di
là del pruning, tendono all’overfitting;
• la stima dell’errore è molto ottimistica, nonostante si stia trattando un
buon campione: nella migliore delle ipotesi, tra errore sul test set e sul
train c’è una differenza quasi del 2%.
8.2.2
Metodo VS
Usiamo ora il 50% dei dati per il training e lasciamo la restante metà
come validation. Anche in questo caso, analizziamo i risultati in Tab. 8.2:
il risultato migliore corrisponde solo alla SVM gaussiana, che effettivamente
è quella che meglio si comporta sul test set. Non solo: la stima dell’errore
sul validation set è decisamente migliore rispetto a quella del training set,
essendo addirittura peggiorativa rispetto al rate ottenuto.
8.2.3
Metodo KCV
Terminiamo l’analisi con la KCV, settando k = 10 e selezionando l’apposita opzione in WEKA explorer tra le “Test options”. Presentiamo in Tab.
8.3 i risultati per la Cross Validation: anche in questo caso, la SVM gaussiana risulta il metodo statistico che meglio si comporta. La stima dell’errore,
in più, è molto buona, dato che la differenza è nell’ordine dello 0.1%.
111
Metodo
NBC
MLP
SVM lin
SVM gauss
DT
Errore KCV
18.93%
3.27%
4.13%
2.73%
4.27%
Errore test
22.96%
4.81%
5.31%
2.84%
3.83%
Tabella 8.3: Risultati per il metodo k–Fold Cross Validation (KCV): in
grassetto, le migliori percentuali ottenute.
8.3
Analisi in WEKA KF
Fino ad ora, nella nostra analisi, abbiamo utilizzato solamente WEKA
explorer. Tra i vari applicativi disponibili in WEKA è però presente anche
un altro strumento molto comodo: WEKA Knowledge Flow, che chiameremo
KF per brevità. KF è molto simile nell’aspetto e nell’utilità al tool Simulink
di MATLAB: in pratica, il modello simulativo viene creato come schema a
blocchi, in cui ad ogni blocco corrisponde una particolare elaborazione sul
dato.
È impensabile riuscire ad analizzare ogni blocco di KF, ma la guida disponibile con il software è abbastanza completa e user–friendly. Noi andremo
a creare, invece, un modello passo–passo per vedere come si può implementare quanto già fatto con WEKA explorer in questo strumento, da molti punti
di vista ancora più potente.
KF è costituito da una serie di tab, ognuno rappresentante: blocchi per
l’input dati; blocchi per l’output dati; filtri da applicare al dataset; algoritmi
per classificazione e regressione; algoritmi di clustering; blocchi per la valutazioni delle performance dei metodi statistici; blocchi per la visualizzazione
dell’output a video.
Ci poniamo come obiettivo la realizzazione di una valutazione comparativa tra una SVM gaussiana e una SVM lineare sul dataset segment con una
KCV a 10 fold. Vediamo passo–passo come fare.
112
8.3.1
Input
Il primo passo corrisponde alla selezione del dataset. Essendo sotto forma
di file arff, selezioniamo il tab per gli input e trasciniamo nello spazio per la
creazione del modello il blocco “ArffLoader”. Clicchiamo col tasto destro e
configuriamo il blocco, selezionando il file per il nostro dataset.
8.3.2
Selezione della classe
Caricato il dataset, siamo interessati ad un problema di classificazione.
Pertanto, dobbiamo definire un attributo come classe: nel tab “Evaluation”,
trasciniamo nel progetto il blocco “Class Assigner”.
A questo punto, dobbiamo connettere al blocco il dataset, caricato al
passo 8.3.1: clicchiamo sul blocco “ArffLoader” col tasto destro e, nella
sottocategoria “Connections”, colleghiamo il dataset con il “Class Assigner”.
Non ci resta che configurare il blocco “Class Assigner”, usando sempre il
tasto destro: selezioneremo l’attributo voluto (class) come classe. Il prefisso
“(Nom)” indica che l’attributo è di tipo nominale.
8.3.3
Creazione delle k fold per la KCV
Per creare le k fold per la cross validation, aggiungiamo il blocco “Cross
Validation Fold Maker”, disponibile sempre nel tab “Evaluation”. Configuriamolo per utilizzare 10 fold, quindi connettiamo il dataset in output dal
blocco “Class Assigner” a “Cross Validation Fold Maker”.
8.3.4
Inserimento dei blocchi per le SVM
A questo punto, non ci rimane che aggiungere i blocchi per la SVM
lineare e la SVM gaussiana. Nel tab “Classifiers”, troviamo “SMO”: trasciniamo due istanze nel nostro progetto, configurandone una per la SVM
lineare (supponiamo C = 100) e l’altra per la SVM gaussiana (C = 100 e
γ = 1).
Aggiungiamo le connessioni: in uscita dal blocco “Cross Validation Fold
Maker”, connettiamo sia “TrainingSet” che “TestSet” (che, in verità, è il
validation set) ai due blocchi per la SVM. A questo punto, tutto è pronto
per la valutazione comparativa: ci manca solo un blocco per elaborare i
risultati e uno per visualizzare questi ultimi a video.
113
8.3.5
Elaborazione dei risultati
Sappiamo che il parametro di valutazione della KCV consiste nell’errore
commesso sulle varie istanze del validation set. Abbiamo, quindi, necessità
di un blocco che riunisca tali valori: “Classifier Performance Evaluator”,
disponibile nel tab “Evaluation”, ha proprio questo scopo.
Aggiunti due blocchi (uno per ogni SVM), connettiamo il “batchClassifier” in uscita dai blocchi “SMO” con “Classifier Performance Evaluator”, in
modo da valutare le performance dei classificatori.
8.3.6
Uscita a video
Ultimo step: porre in uscita a video i nostri risultati. Aggiungiamo, quindi, un blocco “Text Viewer” (disponibile nel tab “Visualization”) e connettiamo le uscite testuali (“text”) dei blocchi “Classifier Performance Evaluator”
al visualizzatore. Non ci resta che eseguire il tutto.
Figura 8.1: Esempio di schema realizzato in WEKA KF.
8.3.7
Configurazione finale ed esecuzione
Abbiamo terminato gli step necessari, dovremmo avere ora a disposizione una struttura tipo quella mostrata in Fig. 8.1. Non ci resta che lanciare
l’analisi: clicchiamo col tasto destro su “ArffLoader” e, nella sottocategoria
“Actions”, optiamo per “Start loading”. Attendiamo il termine dell’esecuzione (ci viene comunicato nella barra dei log sottostante), quindi clicchiamo col
tasto destro sul “Text viewer” e selezioniamo “Show results”: nella finestra
di testo, sulla sinistra, possiamo selezionare i risultati per i metodi inseriti
nel progetto e visualizzarli. È facilmente verificabile che i valori, come ci si
attendeva, sono gli stessi di Tab. 8.3.
114
8.4
Note conclusive
È possibile che, specialmente nel caso si utilizzi la KCV su dataset con un
numero di pattern elevato, i modelli creati per la valutazione di un metodo
statistico siano piuttosto “ingombranti” in termini di occupazione di memoria. Spesso, si deve ricorrere ad un heap più capiente: a questo scopo, è
necessario ricompilare WEKA da riga di comando. In particolare, l’istruzione
di compilazione diventa:
java -Xmx512m -jar weka.jar
identica alla riga di compilazione originaria, presentata nel paragrafo 1.4, a
meno dell’opzione di compilazione -Xmx, indicante la dimensione dello stack,
seguita dalla dimensione di quest’ultimo (nel caso citato, 512 MB).
115
Bibliografia
[1] R. Agrawal e R. Srikant. Fast algorithms for mining association rules in large
databases. In Proc. of the Int. Conf. on Very Large Databases, pagg. 478–499,
1994.
[2] D. Anguita, S. Ridella, e D. Sterpi. Testing the augmented binary multiclass
svm on microarray data. In Proc. of the IEEE Int. Joint Conf. on Neural
Networks, IJCNN 2006, pagg. 1966–1968, 2006.
[3] M. Aupetit. Homogeneous bipartition based on multidimensional ranking.
In Proc. of the European Symposium on Artificial Neural Networks, ESANN
2008, 2008.
[4] V. Barnett. Elements of Sampling Theory. Arnold, 1975.
[5] M. Berry e G. Linoff. Data Mining Techniques for Marketing, Sales, and
Customer Support. John Wiley & Sons, 1997.
[6] C. J. C. Burges. A tutorial on support vector machines for classification.
Data Mining and Knowledge Discovery, 2:121–167, 1998.
[7] J. Cohen. A coefficient of agreement for nominal scales. Educational and
Psychological Measurement, 20(1):37–46, 1960.
[8] C. Cortes e V. Vapnik. Support–vector networks. Machine Learning, 27:273–
297, 1991.
[9] U. Fayaad. Proceedings of the First Int. Conf. on Knowledge Discovery and
Data Mining. Montreal, Canada, 1995.
[10] P. Giudici. Applied Data Mining: Statistical Methods for Business and
Industry. John Wiley & Sons, 2003.
[11] I. Guyon, J. Weston, S. Barnhill, e V. Vapnik. Gene selection for cancer
classification using support vector machines. Machine Learning, 46:389–422,
2002.
[12] G. H. John e P. Langley. Estimating continuous distributions in bayesian
classifiers. In Proc. of the 11th Int. Conf. on Uncertainity in Artificial
Intelligence, pagg. 338–345, 1998.
[13] I. T. Jolliffe. Principal component analysis. In Springer Series in Statistics,
2002.
116
[14] R. Kimball e M. Ross. The Data Warehouse Toolkit (2nd edition). John
Wiley & Sons, 2002.
[15] T. Kohonen. Self–Organizing Maps (3rd edition). Springer, 2001.
[16] M. L. Minsky e S. A. Papert. Perceptrons. Cambridge Press, 1969.
[17] K. Pearson. On lines and planes of closest fit to systems of points in space.
Philosophical Magazine, 2(6):559–572, 1901.
[18] J. C. Plat. Probabilistic outputs for support vector machines and comparison
to regularized likelihood methods. In Advances in Large Margin Classifiers.
MIT Press, 2000.
[19] J. R. Quinlan. Learning with continuous classes. In Proc. of the Australian
Joint Conf. on Artificial Intelligence, pagg. 343–348, 1992.
[20] J. R. Quinlan. C4.5: Programs for Machine Learning. Morgan Kaufmann,
1993.
[21] F. Rosenblatt. The perceptron: A probabilistic model for information storage
and organization in the brain. Psychological Review, 65(6):386–408, 1958.
[22] A. J. Smola e B. Schoelkopf. A tutorial on support vector regression.
Rapporto tecnico, Statistics and Computing, 1998.
[23] V. Vapnik. The Nature of Statistical Learning Theory. Springer, 2001.
[24] Y. Wang e I. H. Witten. Induction of model trees for predicting continuous
classes. In Proc. of the European Conference on Machine Learning, 1997.
117