I am currently revising pointers for my C exam and came across an example that I still cannot comprehend.
Consider the following (partial) code:
int x = 17;
int *ptr = &x;
cout<<*&ptr<<" "<<&ptr<<" "<<ptr<<" "<<*ptr<<endl;
I understand that &ptr
and ptr
are the same, i.e. that print the address of variable x
. I also understand that *ptr
prints out the value inside variable x
, i.e. 17.
However, I cannot understand the first one, i.e. *&ptr
. It prints an address, but I do not know to which it points to. I have tried researching it, but I did not find much on it. What does the *&
combination represent?
CodePudding user response:
ptr
and &ptr
are not the same. &ptr
is the address of ptr
(i.e., a pointer to a pointer).
*
is the dereference operator - it returns the value the pointer points to. So, if you dereference &ptr
, you're asking for "the value that the address of ptr
is pointing to", or ptr
(which, of course, is in turn, the address of x
).
CodePudding user response:
in *&ptr
expression, operator precedence is the same for *
and for &
(but precedence is from right to left). So it just takes address of ptr
(stack address), but then dereferences it, basically that is equivalent to just ptr
.
CodePudding user response:
You have (fantasy memory addresses):
variable value address
x 17 0x0001
ptr == &x 0x0001 0x0002
*
dereferences a pointer. For example *ptr
uses the value of ptr
which is 0x0001
and looks what value it find at that address: 17
.
&
on the other hand is the address-of operator. &x
is the address of x
, it is 0x0001
. The address of x
is ptr
.
&*ptr
is just ptr
.
I understand that &ptr and ptr are the same ...
No they are not. ptr
is the address of x
(0x0001
). &ptr
is the address of ptr
(0x0002
).
CodePudding user response:
One thing that is maybe not so clear from other answers: in an expression like *&ptr
, the dereference operator *
does the inverse operation of the "address_of" operator &
, so that they effectively cancel out when combined, and the result is that *&ptr
is identical to ptr
.
A simple way to think about this is to consider the operation of halving a number (i.e. dividing it by 2) and doubling it (multiplying it by 2). Take any number x
: if you halve it and then double the result, what do you get? You get x
back, of course, because those two operations cancel out. You are starting from a value, applying a function to it, and then applying its inverse function, so that you end up with the original value.
&
and *
work the same way: you have a variable ptr
with its value, you take the address of that variable with &
, and then *
takes that address and gives you the value that is stored there, which is the value of ptr
.
This means that *&ptr
is identical to ptr
, and you can do this *&
trick it as many times as you want: it would be the same if you wrote *&*&*&*&*&ptr
. In case you are wondering, all these operators are evaluated from right to left, because that's what the table of precedence and associativity says (they have the same precedence, 2, and when you have multiple operators with the same precedence you apply them in the order specified by the associativity).