简体   繁体   中英

Do pointers only hold addresses to other variables?

I am a bit confused when it comes to pointers.

Some sample code:

char str1[80];
char *p1;
cout <<"Enter a string"<<endl;
cin >> str1;

p1 = str1;

On the the last line of code, if str1 contains 'Test', how come p1 now contains 'Test'. Isn't p1 still a pointer? I thought pointers only contain addresses to other variables.

p1 doesn't contain Test . It contains the address of a byte in memory that is set to the ASCII value of the character T , followed by e , s , t , and a 0. That address is the address of the array str1 , an 80 char array.

If you try to print str1 or p1 , you'll get the output Test . This is because you cannot pass arrays to functions, so if you try to, the array name will decay into a pointer to the first element, just like p1 . So str1 will decay to a pointer to the T and p1 is already a pointer to the T so you get the same output when printing either because they both point to the same address in memory.

p1 is a pointer.

That means that p1 contains the memory address of the first character of str1 .

When you went to see what p1 "held", you probably did something like cout << p1 , or cout << p1[3] . Either one of these will dereference p1 , treating it as a pointer-to-array-of-characters.

To see the actual value of p1 , try cout << (void*)p1 . This will be the same as the actual value of str1 - a memory location which contains 'T', if you entered "Test".

Pointers hold address, nothing more. Sometimes you dereference pointers to get the data, other times you pass the pointer around to code that will dereference it.

For example :

p1 = 0;  //Point to invalid memory address, but an address nonetheless
p1 = str1 //Point to a valid buffer. p1 now holds an new address, nothing else
if(*p1 == 'A')   //Dereference the pointer (gives a character)
    printf("The first character in str1 is A.\n");

You can emphasis the fact that p1 does not hold data other than the pointer by reorganizing your program like this :

char str1[80];
char *p1;

p1 = str1; //Point to un-initialized memory, your compiler might complain.
           //but p1 is happy. It holds an address, it will never "hold" anything else.

//*p1 is valid (will not crash) but holds random garbage, do not use it!

cout <<"Enter a string"<<endl;
cin >> str1; //Now str1 was initialized

if(*p1 == 'A')   //Dereference the pointer (it is now a character)
    printf("The first character in str1 is A.\n");

Now to emphasis the fact that p1 and str1 are the same thing (the same address in memory), add this to the program :

str1[0] = 'A';   //Put a capital A in str1
if(*p1 == 'A')   //Dereference the pointer (it is now a character)
    printf("Now that we forced an A, this test is always true.\n");

What told you that p1 wasn't a pointer?

Functions and operators like cout::<< and printf are designed to print strings (as well as other data types) so they will appropriately dereference pointer arguments for you: give it a pointer to a string and it will print the string at that address. If you really want it to print the value of the pointer as an address, you have to cast it with (void *) .

Do remember that, for array:

int array[N];

The usage of array would essentially mean &array[0] , and therefore, following are same:

PrintAddress(&array[0]); // void PrintAddress(int*);
PrintAddress(array);

This way, when you do:

int *pAddress;
pAddress = &array[0];
PrintAddress(pAddress);

You can modify second line as:

pAddress = array;

And, just for completeness, following are same:

PrintAddress(&array[2]);
PrintAddress(array+2);

And so the following:

pAddress = array+5;
pAddress = &array[5];
printf("Address: %p\n", (void *)p1);

will print the address (from how to see address of a structure in printf ).

printf("String: %s\n", p1);

will print the string.

The first is the actual content of p1 , the second is what this content means in the context of your program: p1 is a pointer to char , which is the usual way in C to represent strings (ending with a 0 - '\\0' ).

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM