lhk*_*lhk 49 concurrency pass-by-reference go channels
go tour有这个例子用于频道:https://tour.golang.org/concurrency/2
package main
import "fmt"
func sum(a []int, c chan int) {
sum := 0
for _, v := range a {
sum += v
}
c <- sum // send sum to c
}
func main() {
a := []int{7, 2, 8, -9, 4, 0}
c := make(chan int)
go sum(a[:len(a)/2], c)
go sum(a[len(a)/2:], c)
x, y := <-c, <-c // receive from c
fmt.Println(x, y, x+y)
}
Run Code Online (Sandbox Code Playgroud)
在sum函数中修改通道c,并且在函数终止后更改仍然存在.显然c是通过引用传递的,但没有创建指向c的指针.是否通过引用隐式传递了通道?
bea*_*mit 59
从技术上讲它们是被复制的,因为当你使用时make
,你在堆上分配一些东西,所以它在技术上是幕后的指针.但是指针类型没有公开,因此可以将它们视为引用类型.
编辑:从规范:
内置函数make采用类型T,它必须是切片,地图或通道类型,可选地后跟类型特定的表达式列表.它返回类型T的值(不是*T).内存初始化,如初始值一节中所述.
必须先初始化通道才能使用它.Make这样做,因此它可以用作参考类型.
这基本上意味着你可以将它传递给一个函数并写入或读取它.一般的经验法则是,如果您使用make
,new
或者&
,您可以将其传递给另一个函数而不复制基础数据.
所以,以下是"参考"类型:
传入函数时只复制数据类型(数字,bool和结构等).字符串是特殊的,因为它们是不可变的,但不是通过值传递的.这意味着以下内容将无法按预期工作:
type A struct {
b int
}
func f(a A) {
a.b = 3
}
func main() {
s := A{}
f(s)
println(s.b) // prints 0
}
Run Code Online (Sandbox Code Playgroud)
Go中的所有内容都按值传递和分配.某些内置类型(包括通道类型和地图类型)表现为指向某些隐藏内部结构的不透明指针.并且可以通过通道或地图上的操作来修改内部结构.它们从as开始nil
,类似于nil
指针.
归档时间: |
|
查看次数: |
22365 次 |
最近记录: |