说明一下Golang 中 make 和 new 的区别?
参考回答
在 Golang 中,make 和 new 是两个用于内存分配的内建函数,但它们的使用场景和功能有所不同:
make:- 用于初始化并分配内存,只能用于创建
slice、map和channel三种类型。 - 返回的是初始化后的数据结构,而不是指针。
- 用于初始化并分配内存,只能用于创建
new:- 用于分配内存,但不初始化,返回的是指向该内存的指针。
- 可以用于任何类型的内存分配。
示例:
// 使用 make 创建 slice
s := make([]int, 5) // 创建一个长度为 5 的 slice
fmt.Println(s) // 输出: [0 0 0 0 0]
// 使用 new 创建 int 指针
p := new(int) // 分配内存给 int 类型
fmt.Println(*p) // 输出: 0 (初始值)
简单来说:
– 用 make 创建的是三种复杂数据结构(slice、map、channel),且返回初始化后的值。
– 用 new 创建的是任意类型的指针,返回指向未初始化零值的内存地址。
详细讲解与拓展
1. make 的详细讲解:
- 适用类型:
slice、map、channel - 作用: 分配并初始化底层数据结构。
- 返回值: 返回非零值的初始化后的数据结构。
例如:
// slice 示例
s := make([]int, 3, 5)
fmt.Println(len(s), cap(s)) // 输出: 3 5
// map 示例
m := make(map[string]int)
m["key"] = 10
fmt.Println(m) // 输出: map[key:10]
// channel 示例
ch := make(chan int, 2)
ch <- 1
ch <- 2
fmt.Println(<-ch) // 输出: 1
注意: make 不返回指针,因为返回的 slice、map 和 channel 本质上已经是引用类型。
2. new 的详细讲解:
- 适用类型: 任意类型
- 作用: 分配一块内存,但不初始化。
- 返回值: 返回一个指向该内存的指针。
例如:
p := new(int) // 创建一个 int 类型的指针
fmt.Println(*p) // 输出: 0
*p = 100 // 修改值
fmt.Println(*p) // 输出: 100
注意:
– new 仅做内存分配,返回值是指针类型,未初始化的内存中存储的是该类型的零值。
– 一般来说,new 的使用场景较少,因为大多数时候我们更倾向于直接声明变量或使用复合字面值。
拓展知识点:为什么 make 和 new 是分开的?
- Go 语言设计简洁,
make专注于处理复杂数据结构的初始化,这些数据结构往往需要底层运行时的支持,例如slice会自动分配和管理底层数组;map需要构建哈希表。 new则是通用的内存分配工具,适用于所有类型,但你需要手动完成初始化工作。
总结
make: 用于分配并初始化slice、map和channel,返回初始化后的数据结构,常用于 Go 中的复杂类型。new: 用于分配内存,返回的是指向内存地址的指针,适用于所有类型,但不进行初始化。
简单记忆:make 负责 初始化,new 只负责 分配。