c++ - Is always the address of a reference equal to the address of origin? -
this looks basic topic important me.
the following example shows address of reference variable equal address of original variable. know can expect concept of c/c++. however, always guaranteed these addresses equal under circumstance?
#include <iostream> #include <vector> #include <string> class point { public: double x,y; }; void func(point &p) { std::cout<<"&p="<<&p<<std::endl; } int main() { std::vector<point> plist; plist.push_back({1.0,4.0}); plist.push_back({10.0,20.0}); plist.push_back({3.0,5.0}); plist.push_back({7.0,0.4}); std::cout<<"&plist[2]="<<&plist[2]<<std::endl; func(plist[2]); return 0; }
result:
&plist[2]=0x119bc90 &p=0x119bc90
unfortunately, many people confuse logical , physical meaning of c++ references.
logical level
there crucial thing found myself c++ references:
as have initialized reference, becomes unpronounceable. , mean "unpronounceable" fact always when name reference in runtime executable code - automatically variable refers to, there no way can touch reference itself. reference alternative name (an alias) variable.
so if have int i_var = 10; int& i_ref = i;
no matter executable expression form it, mentioning of i_ref
mean i_var
.
also, people find helpful think of reference "self-dereferencing pointer". imagine have pointer int* p
, each , every time refer p
mean *p
. instance, p = 10
mean *p = 10
, &p
mean &(*p)
- address of int
p
pointing too. how logically references work.
it applies code too. have point &p = plist[2];
(occured when called func(plist[2])
) p
, plist[2]
start reference same thing - point
object stored index of 2 in plist
. &plist[2]
, &p
absolutely equal.
type system level
if noticed, used terms "runtime executable code" or "executable expression". let me clarify.
compiler knows difference between a
, b
:
int = 0; int& b = a; std::cout << std::boolalpha << std::is_same_v<decltype(a), decltype(b)>; // -> false
as see a
, b
types different. however, std::is_same_v<decltype(a), decltype(b)>
gets evaluated @ compile time did not consider "executable expression".
physical level
notice, until did not said address of reference , address of variable being referenced same. why? because if think logically - they not.
references have implemented in way, whether or not. believe, in example i_var
, i_ref
compiler replace i_ref
i_var
, physical representation of "reference" never exist. on other hand, if store reference inside class implemented pointer.
although, implementation compiler dependent, if reference is pointer under hood, obvious address of pointer , address of object pointing different.
however, why should care? never know address of reference! in executable expression, when i_ref
imply i_var
, remember?:)
ok, if really-really curious "what address of reference", there 1 case when can figure out - when reference a member of class:
int main() { int var = 10; int& real_ref = var; struct { int& ref; } fake_ref = { var }; std::cout << &var << std::endl; // address of var std::cout << &real_ref << std::endl; // still address of var std::cout << &fake_ref << std::endl; // address of reference var std::cout << sizeof var << std::endl; // size of var std::cout << sizeof real_ref << std::endl; // still size of var std::cout << sizeof fake_ref << std::endl; // size of reference var return 0; }
output on x64 compiler:
000000a9272ffba4 <- same 000000a9272ffba4 <- same 000000a9272ffbc0 <- different 4 <- same 4 <- same 8 <- different (8 on 64 bit , 4 on 32 bit compiler)
wiki
Comments
Post a Comment