Pointers 传递指针与Go中的值
我读过这篇有趣的文章,它与围棋完全无关。作者说的一句话引起了我的注意,下面这句话: 。。。例如,将通道作为函数all的参数传递是有效的,因为Go中的通道就像指向用C实现的通道数据结构的指针一样简单。map和其他一些类型也是如此。但是传递数组或结构的效率很低;相反,我们应该传递指向这些类型的指针Pointers 传递指针与Go中的值,pointers,go,Pointers,Go,我读过这篇有趣的文章,它与围棋完全无关。作者说的一句话引起了我的注意,下面这句话: 。。。例如,将通道作为函数all的参数传递是有效的,因为Go中的通道就像指向用C实现的通道数据结构的指针一样简单。map和其他一些类型也是如此。但是传递数组或结构的效率很低;相反,我们应该传递指向这些类型的指针 为什么在使用某些Go内部类型或结构时传递指针效率很低?传递指针效率并不低。但作者是正确的:因为数组和结构在默认情况下是按值传递的,所以它们的内容会复制到每个新函数调用中。这可能是低效的 根据,数组按值传递
为什么在使用某些Go内部类型或结构时传递指针效率很低?传递指针效率并不低。但作者是正确的:因为数组和结构在默认情况下是按值传递的,所以它们的内容会复制到每个新函数调用中。这可能是低效的 根据,数组按值传递。(切片使用指向引擎盖下阵列的指针,因此它们的传递效率更高。) 与片一样,通道由
make
(至少隐式地)分配,依此类推
因此,在使用结构和实际数组时,通常会传递它们的引用。(有关这方面的更多细节,请参见肖恩的回答。他很好地指出,复制并不总是低效的。有时它是可取的。)上下文与此相关: 然而,围棋的类型体系是如此复杂;程序员需要知道 有关标准类型实现的所有详细信息,请参见 他们可以正确地使用它们。例如,它是有效的 作者说,贴图和通道看起来像值,但在复制时像指针 对于其他数据类型,参数中有一个
*
,这是一个清晰的信号,可以对其进行适当修改。通常,参数的前面也有一个&
,这是另一个参数正在修改的信号
当传递贴图和通道时,这些语法信号不存在。这会导致像这样的意外结果:
类似的批评也适用于像[256]byte
这样的数组和像[]byte
这样的片之间的巨大差异,其中缺少大小是不同复制行为的唯一信号
抛开所有这些不谈,作者错误地将复制与效率低下等同起来。的确,复制有时需要比传递指针更多的CPU周期或内存访问。然而,情况并非总是如此。它取决于结构的大小和编译器执行的优化
复制(即传递值)与传递指针的决定也与函数是否修改参数有关
对于不打算由函数修改的小型结构和数组,按值传递它们。这消除了由于意外修改而导致的一整类错误,甚至比其他语言中使用的
const
更好,因为没有办法欺骗和绕过它。当然,在使用嵌入式指针时一定要小心,包括映射和切片,因为这些指针仍可能在函数内部被修改。谢谢您提供的详细答案。非常感谢。