Вы находитесь на странице: 1из 36

Algortmos e estrutura de dados III

Carlos Oberdan Rolim

Cincia da Computao

Hashing

Motivao
Dada uma tabela com uma chave e vrios valores por linha, quero rapidamente procurar, inserir e apagar registros baseados nas suas chaves
Estruturas de busca sequencial/binria levam tempo at encontrar o elemento desejado. Ex: Arrays e listas
5 2 6 1 7 8 4 9

Ex: rvores 8 2 9 6 4

Motivao

Suponha que voc pudesse criar um array onde qualquer item pudesse ser localizado atravs de acesso direto.
Isso seria ideal em aplicaes do tipo Dicionrio, onde gostaramos de fazer consultas aos elementos da tabela em tempo constante. Ex: Tabela de smbolos em compiladores.

Motivao
Em algumas aplicaes, necessrio obter o valor com poucas comparaes, logo, preciso saber a posio em que o elemento se encontra, sem precisar varrer todas as chaves.
A estrutura com tal propriedade chamada de tabela hash.
20 mod 8 = 4
0 1 2 3 4 5 6

45 mod 8 = 5
7

20 ? 11 ?

64
11 mod 8 = 3

11 20

45 ?

O Tamanho de uma tabela HASH


Um problema que como o espao de chaves, ou seja, o nmero de possveis chaves, muito grande este array teria que ter um tamanho muito grande. Ex: Se fosse uma tabela de nomes com 32 caracteres por nome, teramos 2632 = (25)32 = 2160 possveis elementos. Haveria tambm o desperdcio de espao, pois a cada execuo somente uma pequena frao das chaves estaro de fato presentes.

Para que serve Hashing?

O objetivo de hashing mapear um espao enorme de chaves em um espao de inteiros relativamente pequeno. Isso feito atravs de uma funo chamada hash function.
O inteiro gerado pela hash function chamado hash code e usado para encontrar a localizao do item.

Funes Hashing
Mtodo pelo qual:
As chaves de pesquisa so transformadas em endereos para a tabela (funo de transformao);
Obtm-se valor do endereo da chave na tabela HASH

Tal funo deve ser fcil de se computar e fazer uma distribuio equiprovvel das chaves na tabela
A essa funo d-se o nome de Funo HASHING

Funes Hashing
Seja M o tamanho da tabela:
A funo de hashing mapeia as chaves de entrada em inteiros dentro do intervalo [1..M]

Formalmente:
A funo de hashing h(kj) [1,M] recebe uma chave kj {k0,..,km} e retorna um nmero i, que o ndice do subconjunto mi [1,M] onde o elemento que possui essa chave vai ser manipulado

Funes Hashing

ideal (uniforme) a b c d e 1 2 3 4 5 a b c d e f g

ruim 1 2 3 4 5 6 7 8 9 a b

aceitvel
1 2 3 4 5 6 7 8 9

c
d e f g

f
g

6
7 8 9 10

10

10

Funes Hashing
Existem vrias funes Hashing, dentre as quais:
Resto da Diviso
Meio do Quadrado Mtodo da Dobra Mtodo da Multiplicao Hashing Universal

Resto da Diviso
Forma mais simples e mais utilizada Nesse tipo de funo, a chave interpretada como um valor numrico que dividido por um valor

O endereo de um elemento na tabela dado simplesmente pelo resto da diviso da sua chave por M (Fh(x) = x mod M), onde M o tamanho da tabela e x um inteiro correspondendo chave
0 <= F(x) <= M

Resto da Diviso

Ex: M=1001 e a seqncia de chaves: 1030, 839, 10054 e 2030 Chave Endereo 1030 10054 839 2030 29 53 838 29

Resto da Diviso Desvantagens


Funo extremamente dependente do valor de M escolhido
M deve ser um nmero primo Valores recomendveis de M devem ser >20

Colises

Seja qual for a funo, na prtica existem sinnimos chaves distintas que resultam em um mesmo valor de hashing. Quando duas ou mais chaves sinnimas so mapeadas para a mesma posio da tabela, dizse que ocorre uma coliso.

Colises
Qualquer que seja a funo de transformao, existe a possibilidade de colises, que devem ser resolvidas, mesmo que se obtenha uma distribuio de registros de forma uniforme; Tais colises devem ser corrigidas de alguma forma;

O ideal seria uma funo HASH tal que, dada uma chave 1 <= I <= 26, a probabilidade da funo me retornar a chave x seja PROB(Fh(x)= I) = 1/26, ou seja, no tenha colises, mas tal funo difcil, se no impossvel

Resto da Diviso - Coliso


No exemplo dado, M=1001 e a seqncia de chaves: 1030, 839, 10054 e 2031

Chave Endereo
O valor de h(k) o mesmo para 1030 e 2030: coliso

1030 10054 839 2030

29 53 838 29

Tratamento de Colises
Alguns dos algoritmos de Tratamento de Colises so:
Endereamento Fechado Endereamento Aberto Hashing Linear Hashing Duplo

Endereamento Fechado
Tambm chamado de Overflow Progressivo Encadeado
Algoritmo: usar uma lista encadeada para cada endereo da tabela Vantagem: s sinnimos so acessados em uma busca. Processo simples.
Desvantagens: necessrio um campo extra para os ponteiros de ligao.

Tratamento especial das chaves: as que esto com endereo base e as que esto encadeadas

Endereamento Fechado
No endereamento fechado, a posio de insero no muda. Todos devem ser inseridos na mesma posio, atravs de uma lista ligada em cada uma.
20 mod 5 = 0 18 mod 5 = 3
0 1 2

20

25

25 mod 5 = 0 coliso com 20

3 4

18

Endereamento Fechado
A busca feita do mesmo modo: calcula-se o valor da funo hash para a chave, e a busca feita na lista correspondente. Se o tamanho das listas variar muito, a busca pode se tornar ineficiente, pois a busca nas listas se torna seqencial
0 1 2 3

20

88

32

60

15

11

Endereamento Fechado
obrigao da funo HASH distribuir as chaves entre as posies de maneira uniforme
0 1 2 3 4 5 6

15

10 31

4 88

13 20

Hashing Linear
Tambm conhecido como Overflow Progressivo

Consiste em procurar a prxima posio vazia depois do endereo-base da chave


Vantagem: simplicidade Desvantagem: se ocorrerem muitas colises, pode ocorrer um clustering (agrupamento) de chaves em uma certa rea. Isso pode fazer com que sejam necessrios muitos acessos para recuperar um certo registro. O problema vai ser agravado se a densidade de ocupao para o arquivo for alta

Hashing Linear

27 mod 8 = 3
0 1 2 3 4 5 6 7

27 ?

64

11 20 27

Hashing Linear

Valores: 52, 78, 48, 61, 81, 120, 79, 121, 92 Funo: hash(k) = k mod 13 Tamanho da tabela: 13
0 1 2 3 4 5 6 7 8 9 10 11 12

52 78 79 81 120 121 92

48 61

52 92 78 79

81 121 120

48 61

Hashing Duplo
Tambm chamado de re-hash
Ao invs de incrementar a posio de 1, uma funo hash auxiliar utilizada para calcular o incremento. Esta funo tambm leva em conta o valor da chave.
Vantagem: tende a espalhar melhor as chaves pelos endereos. Desvantagem: os endereos podem estar muito distantes um do outro (o princpio da localidade violado), provocando seekings adicionais

Hashing Duplo
Se o endereo estiver ocupado, aplique uma segunda funo hash para obter um nmero c c adicionado ao endereo gerado pela 1a funo hash para produzir um endereo de overflow
Se este novo endereo estiver ocupado, continue somando c ao endereo de overflow, at que uma posio vazia seja encontrada.

Hashing Duplo
Para o primeiro clculo: h(k) = k mod N Caso haja coliso, inicialmente calculamos h2(K), que pode ser definida como: h2(k) = 1 + ( k mod (N-1) ) Em seguida calculamos a funo re-hashing como sendo: rh(i,k) = ( i + h2(k) ) mod N

Hashing Duplo

Usando h2(k) = 1 + (k mod (n - 1)

Inc(27) = 1 + ( 27 mod (8 - 1) = 6 (3 + 6) mod 8 = 1 H(27) = 27 mod 8 = 3


0 1 2 3 4 5 6 7

27 ?

64 27

11 20 53

Endereamento Aberto Remoo


Para fazer uma busca com endereamento aberto, basta aplicar a funo hash, e a funo de incremento at que o elemento ou uma posio vazia sejam encontrados. Porm, quando um elemento removido, a posio vazia pode ser encontrada antes, mesmo que o elemento pertena a tabela:
27? No Insero do 27

Remoo do 20

64

11 20 27

Busca pelo 27

Fim da busca? Sim

Endereamento Aberto: Remoo

Para contornar esta situao, mantemos um bit (ou um campo booleano) para indicar que um elemento foi removido daquela posio:
27? No

64

11 20 X 27

Fim da busca? No

Esta posio estaria livre para uma nova insero, mas no seria tratada como vazia numa busca.

Tabelas HASH Dinmica

Endereamento Aberto Expanso

Na poltica de hashing, h que chamamos de fator de carga (load factor). Ele indica a porcentagem de clulas da tabela hash que esto ocupadas, incluindo as que foram removidas.

Quando este fator fica muito alto (ex: excede 50%), as operaes na tabela passam a demorar mais, pois o nmero de colises aumenta.
9? 64 1 2 11 4 9 7

Endereamento Aberto Expanso

Quando isto ocorre, necessrio expandir o array que constitui a tabela, e reorganizar os elementos na nova tabela. Como podemos ver, o tamanho atual da tabela passa a ser um parmetro da funo hash.
34 40 X 11 95
Tamanho = 7

Tamanho = 13

40

95

34

11

Endereamento Aberto Expanso

O problema : Quando expandir a tabela? O momento de expandir a tabela pode variar

Quando no for possvel inserir um elemento


Quando metade da tabela estiver ocupada Quando o load factor atingir um valor escolhido A terceira opo a mais comum, pois um meio termo entre as outras duas.

Quando no usar Hashing?

Muitas colises diminuem muito o tempo de acesso e modificao de uma tabela hash. Para isso necessrio escolher bem: - a funo hash - o algoritmo de tratamento de colises - o tamanho da tabela Quando no for possvel definir parmetros eficientes, pode ser melhor utilizar rvores balanceadas (como AVL), em vez de tabelas hash.

Вам также может понравиться