Esplora E-book
Categorie
Esplora Audiolibri
Categorie
Esplora Riviste
Categorie
Esplora Documenti
Categorie
Alberto Montresor
Università di Trento
This work is licensed under the Creative Commons Attribution-NonCommercial-ShareAlike License. To view a
copy of this license, visit http://creativecommons.org/licenses/by-nc-sa/2.5/ or send a letter to Creative
Commons, 543 Howard Street, 5th Floor, San Francisco, California, 94105, USA.
© Alberto Montresor 1
Introduzione
✦ Dizionario (reloaded):
✦ Struttura dati per memorizzare insiemi dinamici di coppie
(chiave, valore)
✦ Il valore è un “dato satellite”
✦ Dati indicizzati in base alla chiave
✦ Operazioni: insert(), remove() e lookup()
✦ Applicazioni:
✦ Le tabelle dei simboli di un compilatore a int
✦ La gestione della memoria nei
b double
sistemi operativi
© Alberto Montresor 2
Introduzione
© Alberto Montresor 3
Notazione
© Alberto Montresor 4
Tabelle a indirizzamento diretto
✦ Implementazione: nil
© Alberto Montresor 5
Tabelle hash 0
✦ Tabelle hash:
U H(k1)
✦ Un vettore A[0..m-1] k1 H(k4)
k4
Una funzione hash k2
K
✦
k5
H: U → {0,..,m-1} k3
H(k2),H(k5)
collisione
✦ Indirizzamento hash:
H(k3)
✦ Diciamo che H(k) è il valore hash della chiave k
✦ Chiave k viene “mappata” nello slot A[H(k)]
m–1
✦ Quando due o più chiavi nel dizionario hanno lo
stesso valore hash, diciamo che è avvenuta una collisione
© Alberto Montresor 6
Problema delle collisioni
✦ Esempio:
✦ Studenti ASD solo negli ultimi tre anni
✦ Distribuiti fra 234.717 e 235.716
✦ H(k) = k - 234.717, m = 1000
© Alberto Montresor 7
he
nasia scorrelato
funzione dalla
hash non struttura essa
è semplice; dell’input (la chiave
deve ricavare stessa).
l’output Da qui il termine “hash”,
(un numero
elato Funzioni
dalla hashdell’input (la chiave stessa). Da qui il termine “hash”,
struttura
glese significa “tritare” o “polpetta”: si sminuzza la chiave in pezzettini che sono
ficain“tritare”
ati modo o “polpetta”:
da formare si intero
un sminuzzache lasia
chiave
il in “casuale”
più pezzettini che sono
possibile. Ovviamente l’al-
✦ Se le collisioni sono inevitabili
da formare un intero che sia il più “casuale” possibile. Ovviamente l’al-
che calcola la funzione hash non è casuale, in quanto se si ricalcola più volte H(k)
la funzione hash non
✦ almeno è casuale,diinminimizzare
cerchiamo quanto se si ilricalcola
loro più volte H(k)
numero
ssa chiave k si ottiene sempre lo stesso valore, ma l’indirizzo hash si comporta da un
k si ottiene sempre lo stesso valore, ma l’indirizzo hash si comporta da un
vista statistico
ico come se fossecome
✦ vogliamo se fosseche
statofunzioni
davvero stato davvero
con uno prodotto
distribuiscano
prodotto lancicon
uniformemente
o più unodile
casuali ouna
più lanci
chiavi casuali
negli indicidi una
[0...m-1] della tabella hash
buona funzione
ione hash hash deveilminimizzare
deve minimizzare il numero
numero di collisioni di collisioni
presenti nel sistema;presenti nel sistema;
✦ Uniformità semplice:
teri
ossibilidefinire
per criteriquesta proprietà
per definire è dettoproprietà
questa uniformitàèsemplice: detta P (k)semplice:
detto uniformità la detta P (k) la
chiave
tà ✦siasia
che kuna inserita
chiave nella
P(k) la
k sia tabella,
inseritasiache
probabilità una
nella chiavesia
tabella, k sia inserita nella tabella
�
✦ sia Q(i) = �
P (k) la probabilità che una chiave qualsiasi, finisca nella
Q(i) = P (k)
cella i. k:H(k)=i
k:H(k)=i
a chiave✦qualsiasi finisca nella
Una funzione celladella
H gode i. Unaproprietà
funzione di gode della proprietà
H uniformità semplice se
ilitàseche
ice ∀i ∈una {0,chiave
...,m − qualsiasi
1} : Q(i)finisca
= 1/m. nella cella i. Una funzione H gode della proprietà
mità
zioni semplice se ∀i ∈ {0,
hash, è conveniente . . . , m −la1}
considerare : Q(i) = 1/m.
rappresentazione binaria bin(k)
chiave kfunzioni
efinire non è numerica,
hash, èbin(k) è data dalla
conveniente concatenazione
considerare della rappre-
la rappresentazione binaria bin(k)
i ciascun
ave k. Secarattere
la chiave cheklanon
compone. In tutti bin(k)
è numerica, i linguaggi di programmazione
è data dalla concatenazione della rappre-
primitiva (chiamiamola ord) che applicata ad un carattere, restituisce un
e binaria di ciascun carattere che la compone. In tutti i linguaggi di programmazione
ro ordinale del carattere nell’insieme dei caratteri ammessi. È altresı̀ utile
ail funzione
numero primitiva
intero
© Alberto Montresor
(chiamiamola
rappresentato ord) che
da una stringa applicata
binaria ad un
b. In questo carattere, restituisce un
modo, 8
Funzioni hash
✦ Per poter ottenere una funzione hash con uniformità semplice, la distribuzione
delle probabilità P deve essere nota
✦ Esempio:
✦ U numeri reali in [0,1] e ogni chiave ha la stessa probabilità di essere scelta,
allora
H(k) = �km�
soddisfa la proprietà di uniformità semplice
✦ Nella realtà
✦ La distribuzione esatta può non essere (completamente) nota
✦ Si utilizzano allora tecniche “euristiche”
© Alberto Montresor 9
Funzioni hash
✦ Assunzioni:
✦ Tutte le chiavi sono equiprobabili: P(k) = 1 / |U|
✦ Semplificazione necessaria per proporre un meccanismo generale
✦ Le chiavi sono valori numerici non negativi
✦ E' possibile trasformare una chiave complessa in un numero
✦ ord(c): valore ordinale del carattere c
✦ bin(k): rappresentazione binaria della chiave k, concatenando i valori
ordinali dei caratteri che lo compongono
✦ int(k): valore numerico associato ad una chiave k
✦ Esempio:
✦ bin(“DOG”) → ord(‘D’) ord(“O”) ord(“G”)
→ 4.476.743
© Alberto Montresor 10
Funzioni hash
✦ Rappresentazione intera
✦ int(“weberb”) = 23·645 +5·644 +2·643 +5·642 +18·641 +32·640 = 24.780.493.966
✦ int(“webern”) = 23·645 +5·644 +2·643 +5·642 +18·641 +14·640 = 24.780.493.984
© Alberto Montresor 11
Funzioni hash - Estrazione
✦ Assunzioni
✦ m=2p
✦ Esempio:
✦ m =28 = 256, bit presi dalla posizione 15 alla posizione 22
✦ bin(“weberb”) = 010111 000101 000010 000101 010010 100000
✦ bin(“webern”) = 010111 000101 000010 000101 010010 001110
✦ da cui si ottiene:
✦ H(“weberb”) = bin(00100001) = 33
✦ H(“webern”) = bin(00100001) = 33
© Alberto Montresor 12
Funzioni hash: XOR
✦ Assunzioni
✦ m=2p
✦ Esempio:
✦ m =28 = 256, 5 gruppi di 8 bit, 40 bit ottenuti con 4 zeri di “padding”
✦ H(“weberb”) = int(01011100⊕01010000⊕10000101⊕01001010⊕00000000)
= int(11000011) = 195
✦ H(“webern”) = int(01011100⊕01010000⊕10000101⊕01001000⊕11100000)
= int(00100001) = 33
© Alberto Montresor 13
Funzioni hash: metodo della divisione
✦ Assunzioni:
✦ m dispari, meglio se primo
✦ Procedimento di calcolo
✦ H(k) = k mod m
✦ Esempio:
✦ m =383
✦ H(“weberb”) = 24.780.493.966 mod 383 = ?
✦ H(“webern”) = 24.780.493.984 mod 383 = 242
© Alberto Montresor 14
Funzioni hash
✦ Vanno bene:
✦ Numeri primi, distanti da potenze di 2 (e di 10)
© Alberto Montresor 15
dopo aver espanso
bit. H(Weberb) a destra bin(k)
= int(11000011) = con
195 quattro
mentrezeri in modo che=bin(k)
H(Webern) 40
sia formato=da33.
int(00100001)
O 7. TABELLE
bit. HASH = int(11000011) = 195 mentre H(Webern) = int(00100001)
H(Weberb) 123 = 33.
Funzioni
Infatti, hash:
indicando ⊕ la somma bit a bit modulo 2, si ottiene:
conMoltiplicazione
Infatti, indicando con ⊕ la somma bit a bit modulo 2, si ottiene:
metodi 11000011 = 01011100
di generazione di indirizzi 01010000
⊕ hash sono i⊕ 10000101
seguenti. I ⊕ 01001010
primi due ⊕ 00000000
presuppongono
✦ Assunzioni
11000011 = 01011100 ⊕ 01010000 ⊕ 10000101 ⊕ 01001010 ⊕ 00000000
00100001
er qualche = 01011100
p; il terzo lavora bene ⊕ 01010000
con tutti i ⊕ 10000101
valori 01001000
di m; il⊕quarto ⊕ 11100000
presuppone m
00100001
✦ m numero = 01011100
qualsiasi ⊕ 01010000
(potenze ⊕ 10000101 ⊕ 01001000 ⊕ 11100000
2 consigliate)
glio se primo):
Benché ✦H(Webern) sia uguale a 33, come nel caso (a), la collisione è stata eliminata.
Benché
C una costante reale,
H(Webern) 0 < Ca<33,
sia uguale 1 come nel caso (a), la collisione è stata eliminata.
one: = int(b), dove è un sottoinsieme
Poiché si usano 6 bit per rappresentare ciascun
H(k) b di pcarattere
bit di bin(k),
della solitamente estratti
chiave, int(bin(Webern)) è
(3) Poiché si usano 6 bit per rappresentare ciascun carattere della chiave, int(bin(Webern)) è
osizioni centrali;
interpretato come un numero
✦ Procedimento diun
calcoloin base 2 = 64.
6
interpretato come numero in base 26 = 64.
(k) = int(b), dove b è dato dalla somma modulo 2, effettuata bit a bit, di diversi
iemi di p bit di = int(bin(Webern))
✦ i = iint(bin(k))
i = int(bin(Webern))
bin(k);
icazione:✦ H(k)==23 ·=64 + 55· 64 + 24 · 64 + 35 numero
64 + 18 64 +1 14 64
5 4 3 2 1 0
�m(iC − �iC�)�, m · ·
23 · 64 + 5 · 64 + 2 · 64 + 5 · 64 + 18 · 64 + 14 · 640 di
dove è un 2qualsiasi (le ·
potenze
bene, anzi sono=consigliate),
64(64(64(64(23
= i è int(bin(k))
64(64(64(64(23 · 64 +
· 645)+e+5)
C2)è++
un
2) numero
5)
+ +
5)18)
+ reale,
+ 14.
18) + 0 < C < 1;
14.
✦ Esempio
ne: H(k) è√uguale al resto della divisione di int(bin(k)) per m.
√
Sia C = ✦ C = ( 1)/2
( 5 − m=
5 − e1)/2 256. Allora
= 256.
.4 (Funzioni hash). Si supponga che leAllora
Sia em
chiavi siano di 6 caratteri alfanumerici.
lunghe sono troncate,
✦ H(Webern) mentre
= �m(iC
H(Webern) chiavi
= −più
�m(iC −corte
�iC�)� =sono
�iC�)� espanse
= �256
�256 a destra con
· 0.9996833801
· 0.9996833801 . spazi.
. . .� Si
==255.
. .� 255.
(A) = 1, ord(B) = 2, . . ., ord(Z) = 26 e ord(b) = 32, dove b indica lo spazio,
Il calcolo
Il calcolo di H(Weberb)
di H(Weberb) è lasciato
è lasciato per esercizio.
per esercizio.
entazione di ogni ordinale su 6 bit. Per le chiavi Weberb e Webern si ottengono
rappresentazioni su 36 bit, dove si sono evidenziati per chiarezza i 6 gruppi di 6 bit
entano i caratteri della chiave:
bin(Weberb)
© Alberto Montresor = 010111 000101 000010 000101 010010 100000 16
Funzioni hash
r1 r0
estrai p bits
H(k)
© Alberto Montresor 17
Funzioni hash - continua
© Alberto Montresor 18
Problema delle collisioni
© Alberto Montresor 19
Tecniche di risoluzione delle collisioni
✦ Si memorizza un puntatore
alla testa della lista nello
slot A[h] della tabella hash k5 k2 k6
✦ Operazioni:
k7 k3
✦ Insert:
inserimento in testa k8
✦ Lookup, Delete: m–1
richiedono di scandire la lista alla ricerca della chiave
© Alberto Montresor 20
rapporto tra il numero di chiavi memorizzate nella tabella e la dimensione della tabella stessa.
In altri termini, tabelle di dimensioni diverse presentano lo stesso tempo di ricerca qualora la
Liste di trabocco: complessità
percentuale di posizioni occupate sia la stessa. Siano:
✦ Teorema:
✦ In tavola hash con concatenamento, una ricerca senza successo richiede un tempo
atteso Ө(1 + α)
✦ Dimostrazione:
✦ Una chiave non presente nella tabella può essere collocata in uno qualsiasi degli
m slot
✦ Una ricerca senza successo tocca tutte le chiavi nella lista corrispondente
✦ Tempo di hashing: 1 +
lunghezza attesa lista: α → Θ(1+α)
1
k1 k4
© Alberto Montresor 22
Liste di trabocco: complessità
✦ Teorema:
✦ In tavola hash con concatenamento, una ricerca con successo richiede un tempo
atteso di Ө(1 + α)
✦ Più precisamente: Ө(1 + α/2)
© Alberto Montresor 23
Liste di trabocco: complessità
© Alberto Montresor 24
Indirizzamento aperto
© Alberto Montresor 25
Indirizzamento aperto
© Alberto Montresor 26
Indirizzamento aperto
© Alberto Montresor 27
Tecniche di ispezione
✦ Nella realtà:
✦ E' difficile implementare il vero uniform hashing
✦ Ci si accontenta di ottenere semplici permutazioni
✦ Tecniche diffuse:
✦ Ispezione lineare
✦ Ispezione quadratica
✦ Doppio hashing
© Alberto Montresor 28
Ispezione lineare
© Alberto Montresor 29
Ispezione quadratica
✦ Sequenza di ispezioni:
✦ L'ispezione iniziale è in H(k)
✦ Le ispezione successive hanno un offset che dipende da una funzione quadratica
nel numero di ispezione i
✦ Solo m sequenze di ispezione distinte sono possibili
© Alberto Montresor 30
Ispezione pseudo-casuale
✦ Sequenza di ispezioni:
✦ L'ispezione iniziale è in H(k)
✦ ri è l’i-esimo elemento restituito da un generatore di numeri casuali fra [0 ... m-1]
✦ Solo m sequenze di ispezione distinte sono possibili
© Alberto Montresor 31
Doppio hashing
© Alberto Montresor 32
Cancellazione
© Alberto Montresor 33
Codice - Hashing doppio
H ASH
I TEM[ ] A % Tabella delle chiavi
I TEM[ ] V % Tabella dei valori
integer m % Dimensione della tabella
H ASH Hash(integer capacità)
H ASH t = new H ASH
t.m ← capacità
t.A ← new Item[0 . . . t.m − 1]
t.V ← new Item[0 . . . t.m − 1]
for i ← 0 to t.m − 1 do t.A[i] ← nil
return t
integer scan(I TEM k, boolean insert)
integer c ← m % Prima posizione deleted
integer i ← 0 % Numero di ispezione
integer j ← H(k) % Posizione attuale
while A[j] �= k and A[j] �= nil and i < m do
if A[j] = deleted and c = m then c ← j
© Alberto Montresor
j ← (j + H �
(k)) mod m 34
for i ← 0 to t.m − 1 do t.A[i] ← nil
Codice
return- Hashing
t doppio
remove(I TEM k)
integer i ← scan(k, false)
if A[i] = k then
© Alberto Montresor 36
Indirizzamento aperto: Complessità hashing doppio
✦ Assunzioni
✦ Hashing uniforme
✦ Nessuna cancellazione
✦ Nella ricerca con successo, tutte le chiavi hanno la stessa probabilità di essere
cercate
✦ Analisi
✦ n chiavi inserite in una tabella di m slot
✦ n < m, ovvero il fattore di carico α < 1
✦ Analisi basata sul valore di α
© Alberto Montresor 37
Indirizzamento aperto: Complessità hashing doppio
✦ Il numero atteso di ispezioni I(α) per una ricerca senza successo è O(1/(1-α))
✦ Esempio: α=0.5, I(α)=2; α=0.9, I(α) =10
✦ A cosa tende queste valore per α → 1?
© Alberto Montresor 38
one uniforme delle chiavi. Le funzioni ottenute al variare di α per i vari metodi di scansion
no, con buona approssimazione,
Complessità - Riassunto le seguenti:
(1 − α)2 + 1 1 − α/2
Lineare 0≤α<1
2(1 − α)2 1−α
1 1
Hashing doppio 0≤α<1 1−α − ln(1 − α)
α
© Alberto Montresor 39
O 7. TABELLE HASH 131
2
(1 − α) + 1 1 1 − α/2
Q uadratica,
p seudocasuale,
hashing dop p io
4
Liste di trab occo
1
3 – ln (1 − α)
α
1+α
2
1 + α/2
✦ Risultato
✦ Fattore di carico dimezzato (tipicamente 0.25)
✦ Nessun elemento deleted
✦ Costi
✦ Costo O(m) per la ristrutturazione nel caso pessimo
✦ Costo ammortizzato costante (vedi dimostrazione per vettori)
© Alberto Montresor 41
Commenti finali
✦ Implementazione
✦ HashMap in Java
✦ hash_map della Standard Template Library del C++
✦ Un’interessante estensione
✦ Distributed Hash Table (DHT)
© Alberto Montresor 42