相关重要总结 :
变量的本质其实就是地址,地址内存储着值,这个变量只是代表着这个地址,变量和数据是分开的,这在python中变量也同理
数组是值类型,传参到函数中会复制成一个副本
切片、map、chan是引用类型,不支持直接比较,只能和nil比较,每个切片会指向一个底层数组
切片的本质就是对底层数组的封装,它包含了三个信息:底层数组的指针、切片的长度(len)和切片的容量(cap)
切片是引用类型,通过赋值,对一个切片的修改会影响另一个切片的内容
copy()函数可以迅速地将一个切片的数据复制到另外一个切片空间中
map是引用类型,必须初始化才能使用,无序,变量默认初始值为nil
new函数只接受一个参数,这个参数是一个类型,new函数返回一个指向该类型内存地址的指针
make也是用于内存分配的,区别于new,它只用于slice、map以及chan的内存创建,返回的还是这三个引用类型本身,二者都是用来做内存分配的

补充
未初始化的切片是nil, 长度和容量都为0,初始化的切片不是nil,即便长度和容量都为0
通过var声明的零值切片可以直接在append使用,无需初始化
扩容往往发生在append, 所以通常都需要用原变量接收append函数的返回值, 这个是重点

具体的坑看代码

nums1 := make([]int, 2)
nums2 := nums1            // 两个变量指向同一块地址

nums2[0] = 111
nums1[1] = 222

fmt.Println(nums1, nums2) // 输出 [111 222] [111 222]

nums1 = append(nums1, 333)

// 这是因为append时会发生扩容,返回的是扩容后的切片地址,所以两个变量指向的地址不一致了,
// nums1指向新的地址,nums2还是指向旧的地址
fmt.Println(nums1, nums2) // 输出 [111 222 333] [111 222]