package main
import (
"fmt"
)
// Entry holds key-value pairs
type Entry struct {
key string
value int
next *Entry
}
// HashMap with fixed size array and chaining for collisions
type HashMap struct {
buckets []*Entry
size int
}
// NewHashMap creates a new hash map
func NewHashMap(size int) *HashMap {
return &HashMap{
buckets: make([]*Entry, size),
size: size,
}
}
// hash function converts key to index
func (hm *HashMap) hash(key string) int {
hash := 0
for _, ch := range key {
hash += int(ch)
}
return hash % hm.size
}
// Put adds or updates key-value
func (hm *HashMap) Put(key string, value int) {
index := hm.hash(key) // get index
entry := hm.buckets[index]
if entry == nil {
hm.buckets[index] = &Entry{key: key, value: value}
return
}
// handle collision by chaining
for entry != nil {
if entry.key == key {
entry.value = value // update existing
return
}
if entry.next == nil {
break
}
entry = entry.next
}
entry.next = &Entry{key: key, value: value}
}
// Get finds value by key
func (hm *HashMap) Get(key string) (int, bool) {
index := hm.hash(key) // get index
entry := hm.buckets[index]
for entry != nil {
if entry.key == key {
return entry.value, true
}
entry = entry.next
}
return 0, false
}
func main() {
hm := NewHashMap(8)
hm.Put("Alice", 123)
hm.Put("Bob", 456)
hm.Put("Carol", 789)
value, found := hm.Get("Bob")
if found {
fmt.Printf("Found Bob's number: %d\n", value)
} else {
fmt.Println("Bob not found")
}
}index := hm.hash(key) // get index
convert key to index to find bucket
if entry == nil { hm.buckets[index] = &Entry{key: key, value: value} return }
store new entry if bucket empty
for entry != nil { if entry.key == key { entry.value = value return } if entry.next == nil { break } entry = entry.next }
handle collision by chaining and update if key exists
entry.next = &Entry{key: key, value: value}
add new entry at end of chain for collision
for entry != nil { if entry.key == key { return entry.value, true } entry = entry.next }
search chain for key to get value