一文带你揭秘Go中new()和make()函数的区别和用途
作者:技术的游戏
Go(或 Golang)是一种现代、静态类型、编译型的编程语言,专为构建可扩展、并发和高效的软件而设计,它提供了各种内置的函数和特性,帮助开发人员编写简洁高效的代码,在本博客文章中,我们将探讨 new() 和 make() 函数之间的区别,了解何时以及如何有效地使用它们
Go(或 Golang)是一种现代、静态类型、编译型的编程语言,专为构建可扩展、并发和高效的软件而设计。它提供了各种内置的函数和特性,帮助开发人员编写简洁高效的代码。其中包括 new() 和 make() 函数,这两个函数乍看起来可能相似,但在 Go 中用于不同的目的,对于内存分配和数据初始化至关重要。
new() 和 make() 函数
new()
和 make()
都是 Go 中的内置函数,用于分配内存。然而,它们用于不同的数据类型和场景:
new() 函数:
new()
用于为值类型(例如整数、浮点数、结构体)分配内存,并返回指向新分配的零值的指针。- 它接受一个参数,即类型,并返回该类型的指针。
make() 函数:
make()
用于创建和初始化切片、映射和通道,这些都是 Go 中的引用类型。- 它根据类型的不同接受两个或三个参数,并返回一个已初始化(非零值)的值,可以立即使用。
理解 new() 函数
new()
函数的语法非常简单,如下所示:
func new(Type) *Type
这里的 Type
表示我们想要为其分配内存的值的类型。让我们看一个如何使用 new()
的示例。
在这个示例中,我们使用 new()
创建了 Person
结构体的一个新实例,然后使用指针分配值给其字段。
package main import "fmt" type Person struct { Name string Age int } func main() { // Using new() to allocate memory for a Person struct p := new(Person) fmt.Printf("%T\n", p) // Accessing struct fields using the pointer p.Name = "Alice" p.Age = 30 // Displaying the values fmt.Println("Name:", p.Name) fmt.Println("Age:", p.Age) }
这个程序将产生如下所示的输出。
> go run main.go *main.Person Name: Alice Age: 30
理解 make() 函数
make()
函数的语法取决于它所用于的类型。
对于切片(Slices)
func make([]Type, len, cap) []Type
Type
:切片将保存的元素类型。len
:切片的初始长度。cap
:切片的容量,这是可选的,并用于指定底层数组的容量。如果未提供,它默认与长度相同。
使用 make()
创建切片的示例:
package main import "fmt" func main() { // Using make() to create a slice of integers numbers := make([]int, 5, 10) // Displaying the slice's length, capacity, and values fmt.Println("Length:", len(numbers)) fmt.Println("Capacity:", cap(numbers)) fmt.Println("Values:", numbers) // Using make() to create a slice of integers numbersWithoutOptional := make([]int, 5) // Displaying the slice's length, capacity, and values fmt.Println("Length:", len(numbersWithoutOptional)) fmt.Println("Capacity:", cap(numbersWithoutOptional)) fmt.Println("Values:", numbersWithoutOptional) }
此程序将产生如下输出。
> go run main.go Length: 5 Capacity: 10 Values: [0 0 0 0 0] Length: 5 Capacity: 5 Values: [0 0 0 0 0]
对于映射(Maps)
func make(map[KeyType]ValueType, initialCapacity int) map[KeyType]ValueType
KeyType
:映射中键的类型。ValueType
:与键关联的值的类型。initialCapacity
:映射的初始容量。这是可选的,但当预先知道元素数量时,可以用于优化性能。
使用 make()
创建映射的示例:
package main import "fmt" func main() { // Using make() to create a map of string keys and int values scores := make(map[string]int) // Adding values to the map scores["Alice"] = 95 scores["Bob"] = 87 // Displaying the map fmt.Println("Scores:", scores) } > go run main.go Scores: map[Alice:95 Bob:87]
对于通道(Channels)
func make(chan Type, capacity int) chan Type
Type
:可以通过通道发送和接收的值的类型。capacity
:通道的缓冲区大小。如果设置为0,通道是无缓冲的。
使用 make()
创建通道的示例:
package main import ( "fmt" "time" ) func main() { // Using make() to create an unbuffered channel of integers ch := make(chan int) // Sending data into the channel using a goroutine go func() { for i := 1; i <= 5; i++ { ch <- i time.Sleep(time.Second) // Simulating some work before sending the next value } close(ch) }() // Receiving data from the channel for num := range ch { fmt.Println("Received:", num) } } > go run main.go Received: 1 Received: 2 Received: 3 Received: 4 Received: 5
结论
在本博客文章中,我们解开了 Go 中的 new()
和 make()
函数的谜团,并解释了它们的区别和用途。总结一下:
- 使用 new() 为值类型分配内存,并获取指向零值的指针。
- 使用 make() 创建和初始化切片、映射和通道(引用类型),并指定它们的类型和初始容量。
理解 new() 和 make() 之间的区别对于在 Go 中进行高效的内存分配和数据初始化至关重要。正确使用这些函数将在您的 Golang 项目中产生更干净和更优化的代码。
以上就是一文带你揭秘Go中new()和make()函数的区别和用途的详细内容,更多关于Go new()和make()函数的资料请关注脚本之家其它相关文章!