Question

I understand the overall meaning of pointers and references(or at least I think i do), I also understand that when I use new I am dynamically allocating memory.

My question is the following:

If i were to use cout << &p, it would display the "virtual memory location" of p. Is there a way in which I could manipulate this "virtual memory location?"

For example, the following code shows an array of ints.

If I wanted to show the value of p[1] and I knew the "virtual memory location" of p, could I somehow do "&p + 1" and obtain the value of p[1] with cout << *p, which will now point to the second element in the array?

int *p;
p = new int[3];

p[0] = 13;
p[1] = 54;
p[2] = 42;
Was it helpful?

Solution

Sure, you can manipulate the pointer to access the different elements in the array, but you will need to manipulate the content of the pointer (i.e. the address of what p is pointing to), rather than the address of the pointer itself.

int *p = new int[3];
p[0] = 13;
p[1] = 54;
p[2] = 42;

cout << *p << ' ' << *(p+1) << ' ' << *(p+2);

Each addition (or subtraction) mean the subsequent (prior) element in the array. If p points to a 4 byte variable (e.g. int on typical 32-bits PCs) at address say 12345, p+1 will point to 12349, and not 12346. Note you want to change the value of what p contains before dereferencing it to access what it points to.

OTHER TIPS

Not quite. &p is the address of the pointer p. &p+1 will refer to an address which is one int* further along. What you want to do is

p=p+1; /* or ++p or p++ */

Now when you do

cout << *p;

You will get 54. The difference is, p contains the address of the start of the array of ints, while &p is the address of p. To move one item along, you need to point further into the int array, not further along your stack, which is where p lives.

If you only had &p then you would need to do the following:

int **q = &p; /* q now points to p */
*q = *q+1;
cout << *p;

That will also output 54 if I am not mistaken.

It's been a while (many years) since I worked with pointers but I know that if p is pointing at the beginning of the array (i.e. p[0]) and you incremented it (i.e. p++) then p will now be pointing at p[1].

I think that you have to de-reference p to get to the value. You dereference a pointer by putting a * in front of it.

So *p = 33 with change p[0] to 33.

I'm guessing that to get the second element you would use *(p+1) so the syntax you'd need would be:

cout << *(p+1)

or

cout << *(++p)

I like to do this:

&p[1]

To me it looks neater.

Think of "pointer types" in C and C++ as laying down a very long, logical row of cells superimposed on the bytes in the memory space of the CPU, starting at byte 0. The width of each cell, in bytes, depends on the "type" of the pointer. Each pointer type lays downs a row with differing cell widths. A "int *" pointer lays down a row of 4-byte cells, since the storage width of an int is 4 bytes. A "double *" lays down a 8-byte per-cell row; a "struct foo *" pointer lays down a row with each cell the width of a single "struct foo", whatever that is. The "address" of any "thing" is the byte offset, starting at 0, of the cell in the row holding the "thing".

Pointer arithmetic is based on cells in the row, not bytes. "*(p+10)" is a reference to the 10th cell past "p", where the cell size is determined by the type of p. If the type of "p" is "int", the address of "p+10" is 40 bytes past p; if p is a pointer to a struct 1000 bytes long, "p+10" is 10,000 bytes past p. (Note that the compiler gets to choose an optimal size for a struct that may be larger than what you'd think; this is due to "padding" and "alignment". The 1000 byte struct discussed might actually take 1024 bytes per cell, for example, so "p+10" would actually be 10,240 bytes past p.)

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top