Quote:
Originally Posted by DaWei
When a reference is passed as an argument, a copy of the objects address is passed. This is one fewer levels of indirection than when a pointer to the object is passed.
A reference is (usually) exactly the same as a pointer, from
an implementation and performance point of view. They are,
in that sense, pure syntactic sugar. The only difference is
that in some cases a reference can be optimized away.
I'm not saying they are a bad thing, they're good for what
they are designed for. It's just incorrect to suggest that
they offer a performance advantage over pointers.
If you still disagree, consider this C++ and its assembly code
(from g++ using -S flag):
Code:
#include <iostream>
using namespace std;
void f( int i, int& r, int* p ) {
++i;
++r;
++*p;
}
int main() {
int i = 0, r = 1, p = 2;
cout<< i <<' '<< r <<' '<< p <<endl;
f( i, r, &p );
cout<< i <<' '<< r <<' '<< p <<endl;
}
I've condensed the assembly for brevity. ## comments are mine.
Code:
...
__Z1fiRiPi: ## f's mangled name: Z1(arbitrary) f(our name) iR(int&) iP(int*) i(int)
pushl %ebp
movl %esp, %ebp
incl 8(%ebp) ## inc value at stack offset 8 (i)
movl 12(%ebp), %eax ## load pointer at stack offset 12 (r)
incl (%eax) ## inc indirect (dereference)
movl 16(%ebp), %eax ## same as for r (p)
incl (%eax)
popl %ebp
ret
...
movl $0, -4(%ebp) ## Load the variables with 0, 1, and 2.
movl $1, -8(%ebp) ## Note their constant addresses (stack offsets).
movl $2, -12(%ebp) ## i is -4, r is -8, p is -12 (relative to ebp)
...
leal -12(%ebp), %eax ## push p's address
pushl %eax
leal -8(%ebp), %eax ## push r's address (same as for p)
pushl %eax
pushl -4(%ebp) ## push i (value)
call __Z1fiRiPi ## call f
...