Pointers 如何从函数调用中获取返回值的指针?

Pointers 如何从函数调用中获取返回值的指针?,pointers,go,Pointers,Go,我只需要一个指向time.time的指针,所以下面的代码似乎无效: /c.go:5:无法获取时间的地址。现在() 我只是想知道为什么?除了先赋值给变量,然后取变量的指针外,还有其他方法吗 package main import "time" func main() { _ = &time.Now() } 可能不令人满意的答案是“你不能这样做,因为规范这么说。”规范说,要在某些东西上使用&,它必须是一个复合文字,并且要可寻址,它必须是变量、指针间接寻址或切片索引操作;或可寻址结

我只需要一个指向time.time的指针,所以下面的代码似乎无效:

/c.go:5:无法获取时间的地址。现在()

我只是想知道为什么?除了先赋值给变量,然后取变量的指针外,还有其他方法吗

package main

import "time"
func main() {
    _ = &time.Now()
}

可能不令人满意的答案是“你不能这样做,因为规范这么说。”规范说,要在某些东西上使用
&
,它必须是一个复合文字,并且要可寻址,它必须是变量、指针间接寻址或切片索引操作;或可寻址结构操作数的字段选择器;函数调用和方法调用绝对不在列表中

实际上,这可能是因为函数的返回值可能没有可用的地址;它可能位于寄存器中(在这种情况下,它肯定不可寻址)或堆栈上(在这种情况下,它有一个地址,但如果它放在一个脱离当前作用域的指针中,则该地址无效。为了保证可寻址性,Go必须执行与将其分配给变量几乎完全相同的操作。但Go是一种语言,它指出,如果要为变量分配存储,它将因为你这么说,并不是因为编译器神奇地决定这么做。所以它不会使函数的结果可寻址


或者我可能想得太多了,他们只是不想让返回一个值的函数和返回多个值的函数有一个特例:)

正如霍布斯所描述的,你不能直接获取函数调用的地址(或者更准确地说是函数的返回值)

还有另一种方法,但它是丑陋的:

p := &[]time.Time{time.Now()}[0]
fmt.Printf("%T %p\n%v", p, p, *p)
输出():

这里发生的是一个
结构
是用一个文本创建的,其中包含一个元素(
time.Now()
)的返回值),切片被索引(第0个元素),第0个元素的地址被获取

因此,只需使用局部变量:

t := time.Now()
p := &t
或辅助函数:

func ptr(t time.Time) *time.Time {
    return &t
}

p := ptr(time.Now())
p := func() *time.Time { t := time.Now(); return &t }()
也可以是一个单行匿名函数:

func ptr(t time.Time) *time.Time {
    return &t
}

p := ptr(time.Now())
p := func() *time.Time { t := time.Now(); return &t }()
或者作为替代方案:

p := func(t time.Time) *time.Time { return &t }(time.Now())
有关更多备选方案,请参见:


另请参阅相关问题:

如果您编写的函数遇到此问题,请将函数更改为返回指针。即使您无法获取返回值的地址,也可以取消对返回值的引用,因此无论您想要指针还是对象都是合适的

func Add(x, y int) *int {
    tmp := x + y
    return &tmp
}

func main() {
    fmt.Println("I want the pointer: ", Add(3, 4))
    fmt.Println("I want the object: ", *Add(3, 4))
}

答案似乎与OP的问题无关,因为示例中提到了time.time()——您无法修改它。