For :
int *a;
a
is an address where an integer can be stored.
&a
is an address where a is stored.
Then, where is &a
stored?
And, where is &(&a)
stored?
And, where is &(&(&a))
stored?
Where does this storing of addresses stop?
For :
int *a;
a
is an address where an integer can be stored.
&a
is an address where a is stored.
Then, where is &a
stored?
And, where is &(&a)
stored?
And, where is &(&(&a))
stored?
Where does this storing of addresses stop?
If you don't explicitly write &a
it will not be stored anywhere. If you do write then the address will be computed and stored either in an unnamed variable (temporary) or a named varible you write.
For example:
functionCall( &a ); // address will be in a temporary variable used for passing the parameter
int** b = &a; // address will be stored in variable b
otherFunctionCall( &&a ); // illegal, since &a is an expression operator & can't be applied to it
&a is the address of a. It is a value, result of operator & applied to a, and is not "stored", and has no address, so &(&a) is invalid. It's like 2+3.
a is a variable of type "address of int"; &a is the address of variable a; &(&a) would be the address of the address of variable a, which makes no sense
a
is not "an address where an integer can be stored". a
is a variable large enough to hold the address of an integer. The only "integer" you can store directly in a
is the address of an integer, viewed as an integer itself:
int *a;
int b;
a = &b;
printf("a is now %x\n", (unsigned int) a);
It is correct that a
itself has an address, which is &a
, but that address is not stored somewhere explicit, at runtime.
At a stretch, you might be able to store something that looks like the integer 0:
a = 0;
But this is just a shorthand syntax for "the NULL pointer", i.e. a pointer value guaranteed to not be the address of any actual object.
Not quite. a
is a variable in which an address of some integer may be stored. &a
is the address of a
, i. e. the address of the variable a
, which may contain an address of some integer.
Very Important: until and unless an address of something is assigned to a
, it is an uninitialized pointer. Trying to use whatever it points to will lead to unpredictable results, and will likely crash your program.
You can have a pointer to a pointer.
Ex:
void foo(int **blah)
{
int *a = *blah;
...
}
A pointer does take up memory. It's just a small container that holds the address of something. It just can't take up "no space" because everything in the computer is represented somehow by numbers. It's just that as far as C/C++ is concenred, int *a is simply a pointer to an object and takes up no space. That is to keep you from having to manage any sort of memory... it keeps the machine seperated from the code.
You can keep going forever:
int value = 742;
int *a = &value;
void *b = &a;
void *c = &b;
void *d = &c;
You wouldn't put it on a single line without assigning it to anything - in that case it would be invalid.
&a is a number which is an rvalue: you can store it somewhere if you want to in a variable you will have declared or allocated, of type int*.
To wit:
int a = 42;
&a; /* this does not store the address of a because you've not assigned the value to a variable */
int **aptr = &a; /* aptr is on the stack */
int **aptr2 = (int*)malloc(sizeof(int*));
aptr2 = &a; /* aptr2 is in the heap */
&(&a) is not legal syntax. If you want a pointer to a pointer to an int:
int b = 39;
int *bptr = &b;
int **ptr2bptr = &bptr;
You have to build up the levels of indirection.
With the above you can then do this if you want:
printf("%d\n", *aptr);
printf("%d\n", *aptr2);
printf("%d\n", *bptr);
printf("%d\n", **ptr_to_bptr);
Producing output of:
42
42
39
39
int *a
is a variable the size of a pointer, just like int b
would an automatic int variable.
If this declaration is in a function, that variable is automatic and stored on the stack
at runtime (a simple stack decrement allocates memory for it).
If the declaration is global, then 'a' is simply mapped in executable's .DATA
area.
Any more & signs appended can 'create storage', because of the temporary variables you're using to hold'em ;) :
b = &a; //the address in the executable's .DATA or on the stack (if `a` auto)
c = &b; //the address of `b` on the stack, independent of `a` or `&a`
d = &c; //the address of `c` on the stack, independent of `a` or `&a`
z = &(&a); //error: invalid lvalue in unary '&'
The last line complains about the fact that &
requires the operand to be a lvalue
. That is, something assignable - like b
and c
above. (&a)
as is a result of an expression which is not stored anywhere, therefore is not a lvalue
.
int* a;
This line simply declares a pointer to an integer. That pointer has a memory location, which you can get the address of using &a. & is an operator that returns the address of whatever it is run on. But if you do not assign this value anywhere, there is no further &-ing possible.
As to your question as to where &a is stored, most likely in a register. If you do not use the value, it will be immediately discarded. (And registers do not have memory addresses, which is why you cannot do &(&a))
At the crux of your problem seems to be a lack of understanding of the physical nature of memory and pointers. Not how the code works. As Im sure you know, physical memory is comprised of a large group of adjacent cells. The addresses of these cells are fixed and hard-coded by the computer itself, not by software apps or the programming language that you use. When you refer to &a, you are referring to the physical block of memory that is currently holding your value you've stored within the computers ram. "a" is simply a name that you've given the computer so that it knows exactly what block of memory to find the value that you've stored. I think that pretty much covers memory address.
Lets go over pointers now. A pointer is yet another memory address, that is referred to by the computer. It has whatever name that you give it. In this case it should be called something else besides the same name that you gave your first value. Lets call it "b". Based on how you declared it. b's memory location is only capable of holding one type of data....another memory location.... so when I say: b= &a I'm saying that the memory address of 'b'(which is designed only to hold memory addresses), is to hold the memory address of 'a'. Meanwhile on the other side of town, the memory address of 'a' has an integer stored in it.
I hope that this didnt get confusing, I tried not to get all techno-babble on you here. If youre still confused. Post again, Ill explain with code next time.
-UBcse