Junior
Kako funkcioniše tabela heš?
sobes.tech АИ
Одговор од АИ
Hash tabela (hash table) je struktura podataka koja implementira asocijativni niz.
Princip rada:
- Hashiranje. Za svaki ključ (key) se izračunava hash kod (hash code) pomoću hash funkcije (hash function). Hash kod je celobrojna vrednost.
- Indeksiranje. Hash kod se koristi za određivanje indeksa (index) u nizu (ili vektoru) unutrašnje strukture hash tabele. Obično se indeks računa kao
hash_code % array_size, gde jearray_sizeveličina niza. - Čuvanje. Na pronađeni indeks u nizu se čuva povezana vrednost (value) sa ključem.
Problemi i rešenja:
- Kolizije. Različiti ključevi mogu dati isti hash kod i, shodno tome, isti indeks u nizu. To se naziva kolizija.
- Metode rešavanja kolizija:
- Metod lančanog rešavanja (Separate Chaining): U svakoj ćoški niza se čuva lista (lista, vektor i sl.) parova "ključ-vrednost". Pri koliziji, nova par se dodaje u tu listu. Pri pretraživanju po indeksu, pregledava se odgovarajuća lista da bi se pronašao željeni ključ.
- Metod otvorene adresacije (Open Addressing): Pri koliziji, traži se druga slobodna ćoška u nizu po određenom pravilu (probijanje).
- Linearna proba (Linear Probing): Redom se proveravaju ćoške
index + 1,index + 2i tako dalje, modula veličine niza. - Kvadratna proba (Quadratic Probing): Proveravaju se ćoške
index + 1^2,index + 2^2i tako dalje, modula veličine niza. - Duple hashiranje (Double Hashing): Koristi se druga hash funkcija za određivanje koraka provere.
- Linearna proba (Linear Probing): Redom se proveravaju ćoške
- Metode rešavanja kolizija:
Prednosti:
- U proseku, operacije umetanja, brisanja i pretraživanja se obavljaju sa složenošću O(1).
Nedostaci:
- U najgorem slučaju (npr. pri velikom broju kolizija ili lošoj hash funkciji), složenost operacija može dostići O(n), gde je n broj elemenata.
- Zahteva dodatnu memoriju (npr. za liste kod metode lančanog rešavanja ili za proboj kod otvorene adresacije).
Primer upotrebe u C++ (std::unordered_map):
#include <unordered_map>
#include <string>
#include <iostream>
int main() {
// Kreiranje hash tabele (unordered_map)
std::unordered_map<std::string, int> starosti;
// Umetanje elemenata
starosti["Alice"] = 30;
starosti["Bob"] = 25;
starosti["Charlie"] = 35;
// Dobijanje vrednosti po ključu
std::cout << "Starost Alice: " << starosti["Alice"] << std::endl;
// Pretraživanje elementa
if (starosti.count("Bob")) {
std::cout << "Bob je u mapi." << std::endl;
}
// Brisanje elementa
starosti.erase("Charlie");
return 0;
}