A reference is not an object. Instead, a reference is just another name for an already existing object.
也就是说引用类型并不是像值类型或者指针类型那样是一个具体的内存对象,而仅仅是对某个变量的别名,它必须和某个变量一一绑定。
Go provides a built-in map type that implements a hash table.
Map types are reference types, like pointers or slices.
也就是说map和slice的原理一致,再看看源码runtime/map.go对map的创建:
1
2
3
4
5
6
7
8
9
10
11
12
// makemap implements Go map creation for make(map[k]v, hint).// If the compiler has determined that the map or the first bucket// can be created on the stack, h and/or bucket may be non-nil.// If h != nil, the map can be created directly in h.// If h.buckets != nil, bucket pointed to can be used as the first bucket.funcmakemap(t*maptype,hintint,h*hmap)*hmap{mem,overflow:=math.MulUintptr(uintptr(hint),t.bucket.size)ifoverflow||mem>maxAlloc{hint=0}......
以及hmap结构体:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
// A header for a Go map.typehmapstruct{// Note: the format of the hmap is also encoded in cmd/compile/internal/gc/reflect.go.// Make sure this stays in sync with the compiler's definition.countint// # live cells == size of map. Must be first (used by len() builtin)flagsuint8Buint8// log_2 of # of buckets (can hold up to loadFactor * 2^B items)noverflowuint16// approximate number of overflow buckets; see incrnoverflow for detailshash0uint32// hash seedbucketsunsafe.Pointer// array of 2^B Buckets. may be nil if count==0.oldbucketsunsafe.Pointer// previous bucket array of half the size, non-nil only when growingnevacuateuintptr// progress counter for evacuation (buckets less than this have been evacuated)extra*mapextra// optional fields}
In the very early days what we call maps now were written as pointers, so you wrote *map[int]int.
We moved away from that when we realized that no one ever wrote map without writing *map.
That simplified many things but it left this issue behind as a complication.
funcmakechan(t*chantype,sizeint)*hchan{...}typehchanstruct{qcountuint// total data in the queuedataqsizuint// size of the circular queuebufunsafe.Pointer// points to an array of dataqsiz elementselemsizeuint16closeduint32elemtype*_type// element typesendxuint// send indexrecvxuint// receive indexrecvqwaitq// list of recv waiterssendqwaitq// list of send waiterslockmutex}