Create A Map In Go, And What
Fast recall
Quick revision
Core answer
Whether you understand Maps Make And Literal beyond memorized syntax.
Giving a definition without explaining a practical trade-off.
Connect the concept to a small production example and state its complexity or failure mode.
Interview-ready guide
Interview answer
Two working ways: the make form for runtime-populated maps, and the literal form when the initial contents are known at code time.
m := make(map[string]int) // empty, ready for writes
m["count"] = 3
defaults := map[string]int{ // starts with contents
"retries": 3,
"timeout": 30,
}And one broken way: declaring the var and writing before initializing.
var m map[string]int // nil — header exists, no buckets
m["k"] = 1 // panic: assignment to entry in nil mapThe asymmetry surprises people: reads on that same nil map work fine — a lookup returns the zero value, len is 0, range runs zero iterations. Only the write panics. The why: a map value is a pointer to a hash structure; nil points at nothing, so a write has nowhere to put the entry, while a read of 'nothing' can honestly answer 'not present, here's your zero value.'
So the rule is simple: make() (or a literal) before any write. Reads on nil are safe; the panic is write-only, and it's the most common map runtime error in beginner Go.
Create A Map In Go, And What
Direct Answer
make(map[string]int) or a literal map[string]int{"a": 1}. A nil map reads fine (zero values) but writes panic: assignment to entry in nil map.
Deep Dive & Architecture
Why the write-only panic? Look at what the two operations need:
A read asks 'is there an entry with key k, and what's its value?' On a nil map, the honest answer is 'no such entry' — which the runtime expresses as (zero value, not-present). No structure needed; absence is expressible without storage.
A write asks 'put this entry somewhere findable.' That needs a bucket array, hash seeds, growth machinery — the whole map structure that make() allocates. With a nil pointer to that structure, there's nowhere to put it. Panic is the runtime refusing to pretend.
The comparison with slices clarifies the design: a nil slice CAN be appended to, because append's allocate-path creates the backing storage on demand — a slice header alone is enough to start. A map can't be lazily created because the map value is a pointer to an ALREADY-COMPLETE structure; there's no 'grow into it' path the way a slice header grows into its array. So var s []int; s = append(s, x) is fine, var m map[string]int; m[x] = 1 panics — the asymmetry is structural, not arbitrary.
The bug pattern it creates: passing a nil map into a function that populates it. The fix is return-the-map (the function makes and returns it) rather than fill-the-parameter — which is also just cleaner Go.
Common Mistakes & Pitfalls
Giving a definition without explaining a practical trade-off.
Check your understanding
Answer these without looking back at the article.
- When would you use Maps Make And Literal in a real project?
- How would you compare Maps Make And Literal with an alternative?
- What is a common mistake when using Maps Make And Literal?
Looking for a structured roadmap?
Every module on this page is also part of the full Java backend interview track.