通过值传递,通过引用传递还是通过指针传递的性能成本? [英] Performance cost of passing by value vs. by reference or by pointer?

查看:86
本文介绍了通过值传递,通过引用传递还是通过指针传递的性能成本?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

让我们考虑一个对象foo(可以是intdouble,自定义structclass等).我的理解是,通过引用函数传递foo(或仅传递指向foo的指针)会带来更高的性能,因为我们避免制作本地副本(如果foo大的话可能会很昂贵).

但是,从答案此处看来,实际上,无论所指向的是什么,在64位系统上的指针的大小都可以为8个字节.在我的系统上,float是4个字节.这是否意味着如果foo的类型为float,则仅通过值传递foo而不是提供指向它的指针更有效率(假设没有其他约束会导致在函数内部使用比另一种更有效的代码)?

解决方案

这取决于您所说的成本",以及主机系统(硬件,操作系统)相对于操作的属性.

如果您的成本衡量标准是内存使用情况,那么成本的计算就很明显-累加要复制内容的大小.

如果您的衡量标准是执行速度(或效率"),则游戏会有所不同.硬件(以及操作系统和编译器)往往会通过专用电路(机器寄存器及其使用方式)针对复制特定大小的事物的操作性能进行优化.

例如,对于一台机器来说,具有导致最佳位置"的架构(机器寄存器,内存架构等)是很常见的-复制某些大小的变量最有效",但是复制较大的OR SMALLER变量则不是如此.较大的变量将花费更多的复制成本,因为可能需要对较小的块进行多次复制.较小的变量可能还会花费更多,因为编译器需要将较小的值复制到较大的变量(或寄存器)中,对其进行操作,然后再将值复制回.

带有浮点的示例包括一些cray超级计算机,它们本机支持双精度浮点(在C ++中为aka double),并且所有在单精度上的操作(在C ++中为aka float)都在软件中进行了仿真.一些较旧的32位x86 CPU也可以在内部使用32位整数,由于对32位的转换,对16位整数进行操作需要更多的时钟周期(对于较新的32位或64位处理器则不是这样.位x86处理器,因为它们允许将16位整数复制到32位寄存器或从32位寄存器复制16位整数,并对其进行操作,从而减少了此类惩罚.

不费吹灰之力的是,按值复制非常大的结构将比创建和复制其地址的效率低.但是,由于上述因素,最好按值复制某件东西"和最好通过其地址"之间的交叉点不太清楚.

指针和引用倾向于以相似的方式实现(例如,按引用传递可以与传递指针相同的方式实现),但这不能保证.

唯一可以确定的方法是对其进行测量.并意识到测量结果在系统之间会有所不同.

Let's consider an object foo (which may be an int, a double, a custom struct, a class, whatever). My understanding is that passing foo by reference to a function (or just passing a pointer to foo) leads to higher performance since we avoid making a local copy (which could be expensive if foo is large).

However, from the answer here it seems that pointers on a 64-bit system can be expected in practice to have a size of 8 bytes, regardless of what's being pointed. On my system, a float is 4 bytes. Does that mean that if foo is of type float, then it is more efficient to just pass foo by value rather than give a pointer to it (assuming no other constraints that would make using one more efficient than the other inside the function)?

解决方案

It depends on what you mean by "cost", and properties of the host system (hardware, operating system) with respect to operations.

If your cost measure is memory usage, then the calculation of cost is obvious - add up the sizes of whatever is being copied.

If your measure is execution speed (or "efficiency") then the game is different. Hardware (and operating systems and compiler) tend to be optimised for performance of operations on copying things of particular sizes, by virtue of dedicated circuits (machine registers, and how they are used).

It is common, for example, for a machine to have an architecture (machine registers, memory architecture, etc) which result in a "sweet spot" - copying variables of some size is most "efficient", but copying larger OR SMALLER variables is less so. Larger variables will cost more to copy, because there may be a need to do multiple copies of smaller chunks. Smaller ones may also cost more, because the compiler needs to copy the smaller value into a larger variable (or register), do the operations on it, then copy the value back.

Examples with floating point include some cray supercomputers, which natively support double precision floating point (aka double in C++), and all operations on single precision (aka float in C++) are emulated in software. Some older 32-bit x86 CPUs also worked internally with 32-bit integers, and operations on 16-bit integers required more clock cycles due to translation to/from 32-bit (this is not true with more modern 32-bit or 64-bit x86 processors, as they allow copying 16-bit integers to/from 32-bit registers, and operating on them, with fewer such penalties).

It is a bit of a no-brainer that copying a very large structure by value will be less efficient than creating and copying its address. But, because of factors like the above, the cross-over point between "best to copy something of that size by value" and "best to pass its address" is less clear.

Pointers and references tend to be implemented in a similar manner (e.g. pass by reference can be implemented in the same way as passing a pointer) but that is not guaranteed.

The only way to be sure is to measure it. And realise that the measurements will vary between systems.

这篇关于通过值传递,通过引用传递还是通过指针传递的性能成本?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆