慕妹3146593
指针可能会转义到堆中,也可能不转义,具体取决于您的使用案例。编译器非常智能。例如,给定:type Person struct { b, c int}func foo(b, c int) int { bob := &Person{b, c} return bob.b}该函数将编译为:foo TEXT "".foo(SB) MOVQ "".b+8(SP), AX MOVQ AX, "".~r2+24(SP) RET它全部位于此处的堆栈上,因为即使它是指针,它也不会逃脱此函数的作用域。bob但是,如果我们考虑轻微的(尽管是人为的)修改:var globalBob *Personfunc foo(b, c int) int { bob := &Person{b, c} globalBob = bob return bob.b}然后转义,并将编译为:bobfoo TEXT "".foo(SB), ABIInternal, $24-24 MOVQ (TLS), CX CMPQ SP, 16(CX) PCDATA $0, $-2 JLS foo_pc115 PCDATA $0, $-1 SUBQ $24, SP MOVQ BP, 16(SP) LEAQ 16(SP), BP LEAQ type."".Person(SB), AX MOVQ AX, (SP) PCDATA $1, $0 CALL runtime.newobject(SB) MOVQ 8(SP), AX MOVQ "".b+32(SP), CX MOVQ CX, (AX) MOVQ "".c+40(SP), CX MOVQ CX, 8(AX) PCDATA $0, $-2 CMPL runtime.writeBarrier(SB), $0 JNE foo_pc101 MOVQ AX, "".globalBob(SB) foo_pc83: PCDATA $0, $-1 MOVQ (AX), AX MOVQ AX, "".~r2+48(SP) MOVQ 16(SP), BP ADDQ $24, SP RET如您所见,它调用 .newobject这些反汇编列表由 https://godbolt.org/ 生成,在 amd64 上为 go 1.16 生成