Go 函数和方法可以返回多个值。
func learnMultiple(x, y int) (sum, prod int) {
return x + y, x * y // return two values
}
总和,产品 := learnMultiple(10, 50)
它类似于返回一个元组吗?
我来自红宝石之地,在那里我可以返回一个数组和一个
sum, prod = ["60","500"]
Go 函数和方法可以返回多个值。
func learnMultiple(x, y int) (sum, prod int) {
return x + y, x * y // return two values
}
总和,产品 := learnMultiple(10, 50)
它类似于返回一个元组吗?
我来自红宝石之地,在那里我可以返回一个数组和一个
sum, prod = ["60","500"]
我们可以轻松查看一些编译后的代码来确认幕后发生的事情。
考虑这个片段:
func f() (a, b byte) {
return 'x', 'y'
}
func main() {
a, b := f()
println(a, b)
}
如果我们反汇编创建的 ELF 二进制文件,你会看到类似这样的内容(内联被禁用,因此我们可以看到调用发生):
0000000000400c00 <main.f>:
400c00: c6 44 24 08 78 movb $0x78,0x8(%rsp)
400c05: c6 44 24 09 79 movb $0x79,0x9(%rsp)
400c0a: c3 retq
0000000000400c10 <main.main>:
(...)
400c25: 48 83 ec 10 sub $0x10,%rsp
400c29: e8 d2 ff ff ff callq 400c00 <main.f>
400c2e: 48 0f b6 1c 24 movzbq (%rsp),%rbx
400c33: 48 89 d8 mov %rbx,%rax
400c36: 48 0f b6 5c 24 01 movzbq 0x1(%rsp),%rbx
(...)
所以f
只需将结果字节放入堆栈中,然后main
将它们取回并放入工作寄存器中。不同的编译器也可能选择在两个范围之间将这些值直接传递到寄存器中。
这一切都类似于 C 语言的编译器所做的,除了它的规范只定义了一个返回值。
它类似于返回一个元组,因为某些语言(如 python)使用元组来实现多个返回值。
但是在 Go 中没有元组这样的东西。返回一个值的函数会在堆栈上分配一个槽来保存它。返回两个值的函数会在堆栈上分配两个槽来保存它们。等等……</p>