C++study pointer explanation

Source: Internet
Author: User

C + + pointers detailed the concept of pointers

A pointer is a special variable, and the value stored in it is interpreted as an address in memory. To make sense of a pointer, you need to be aware of the four aspects of the pointer: the type of pointer, the type that the pointer points to, the value of the pointer, the memory area that the pointer points to, and the memory area occupied by the pointer itself. Let's explain separately.

Let's declare a few pointers for example:

Example one:

int *ptr;  
Char *ptr;
int **ptr;
int (*ptr) [3];
int * (*PTR) [
type of pointer

From a grammatical point of view, you simply remove the pointer name from the pointer declaration statement, and the remainder is the type of the pointer. This is the type that the pointer itself has. Let's look at the types of pointers in example one:

 int *ptr; // 
Span style= "color: #0000ff;" >char *ptr; //
Span style= "color: #0000ff;" >int **ptr; //
Span style= "color: #0000ff;" >int (*ptr) [3]; // int * (*ptr) [4]; //

What do you think? Is it easy to find out the type of pointers?

the type that the pointer points to

When you use a pointer to access the memory area pointed to by the pointer, the type that the pointer points to determines what the compiler will look for in that memory area.

Syntactically, you only have to remove the pointer name and the pointer to the left of the name in the pointer declaration, and all that remains is the type that the pointer points to. For example:

 int *ptr; // 
Span style= "color: #0000ff;" >char *ptr; //
Span style= "color: #0000ff;" >int **ptr; //
int (*ptr) [3]; // int * (*ptr) [4]; //

In the arithmetic operation of a pointer, the type that the pointer points to has a great effect.

The type of the pointer (that is, the type of the pointer itself) and the type that the pointer points to are two concepts. As you become more familiar with C, you will find that the concept of "type", which is mixed with pointers, is divided into "types of pointers" and "types pointed to by pointers", which is one of the key points of mastery of pointers. I read a lot of books, found that some poorly written books, the pointer to the two concepts stirred together, so look at the contradiction between the book, the more confused look.

the value of the pointer


The value of the pointer is the value stored by the pointer itself, which is treated as an address by the compiler, not a generic value. In a 32-bit program, the value of all types of pointers is a 32-bit integer because the memory address in the 32-bit program is all 32 bits long.

The memory area that the pointer points to is the memory address from which the value of the pointer is represented, and the length of the memory area of sizeof (the type the pointer is pointing to). Later, we say that the value of a pointer is XX, which is equivalent to saying that the pointer to an XX-led address of a piece of memory area; we say that a pointer points to a region of memory, which is equivalent to saying that the value of the pointer is the first address of the memory area.

The memory area that the pointer points to and the type that the pointer points to are two completely different concepts. In example one, the pointer points to a type that already exists, but because the pointer is not initialized, the memory area it points to is nonexistent, or meaningless.

Later, every time you encounter a pointer, you should ask: What is the type of this pointer? What type is the pointer pointing to? Where does the pointer point?

the memory area occupied by the pointer itself

How much memory does the pointer itself occupy? You just have to use the function sizeof (the type of the pointer) to find out. In a 32-bit platform, the pointer itself occupies a length of 4 bytes.

The concept of memory occupied by the pointer itself is useful when judging whether a pointer expression is an lvalue.

arithmetic operations of pointers

The pointer can add or subtract an integer. The meaning of this operation of the pointer is not the same as that of the usual numerical subtraction operation. For example:
Example two:

Char a[20];  
int *ptr=a;
...
...
ptr++;


In the example above, the type of the pointer ptr is int*, and the type it points to is int, which is initialized to point to the shaping variable A. In the 3rd sentence, the pointer ptr is added 1, which is handled by the compiler: it adds the value of the pointer ptr to sizeof (int), and in the 32-bit program, it is added 4. Since the address is in bytes, the address pointed to by PTR is incremented by 4 bytes from the address of the original variable A to the high address direction.
Since the length of the char type is one byte, the original ptr is the four bytes starting at Unit No. 0 of array A, pointing to the four bytes from array a starting at unit 4th.
We can use a pointer and a loop to iterate through an array, looking at an example:
Example three:

int array[20];  
int *ptr=array;
...
code that assigns values to an integer array is omitted here.

For (i=0;i<




This example adds 1 to the value of each cell in an integer array. Because each loop has a pointer ptr plus 1, each loop has access to the next cell of the array. Look again at the example:

Example four:

Char a[20];  
int *ptr = A;
...
...
5;


In this example, PTR is added with 5, and the compiler handles this by adding the value of the pointer ptr to 5 by sizeof (int), which adds 5 times 4=20 to the 32-bit program. Because the unit of the address is byte, the current PTR points to an address that is 20 bytes to the high address direction than the address pointed to by PTR after 5. In this example, PTR, which is not added to 5, points to the four bytes starting at Unit No. 0 of array A, plus 5, and PTR points to the legal range of array A. Although this situation may be problematic in application, it is syntactically possible. This also shows the flexibility of the pointer.

If PTR is subtracted by 5 in the example above, then the process is much the same, except that the value of PTR is subtracted by 5 by sizeof (int), and the new PTR points to an address that moves 20 bytes to the lower address direction than the address pointed to by the original PTR.

Summing up, after a pointer ptrold plus an integer n, the result is a new pointer ptrnew,ptrnew of the same type as the Ptrold, and the same type that ptrnew points to and the type that ptrold points to. The value of ptrnew will increase by N by sizeof (the type that the Ptrold points to) by more than the value of Ptrold. That is, the memory area pointed to by Ptrnew will move n by sizeof (the type that the Ptrold points to) bytes than the memory area pointed to by Ptrold to the high address direction. After a pointer ptrold minus an integer n, the result is a new pointer ptrnew,ptrnew of the same type as the Ptrold, and the same type that ptrnew points to and the type that ptrold points to. The value of ptrnew will be less than the value of Ptrold by sizeof (the type that the Ptrold points to) bytes, that is, the memory area that the ptrnew points to will move n by sizeof (the type that the Ptrold points to) than the memory area pointed to by Ptrold A byte.

Operators & and *

Here & is the fetch address operator, * is ... The book is called the "indirect operator." The result of the &a operation is a pointer, the type of the pointer is a type of a, a pointer to the type of a, the pointer to the address, that is the address of a. The result of *p's operation is very multifarious. In short *p The result is what P points to, this thing has these characteristics: its type is the type of P, which occupies the address that P points to.

Example five:

int a=12;
int b;
int *p;
int **ptr;
p=&a;//&a is a pointer, the type is int*, the type is int, and the address that points to is the address of a.
*p=24; *p, where its type is int, and it occupies the address that P points to, it is clear that *p is the variable A.
Ptr=&p; &p is a pointer, the type of the pointer is the type of P plus a *, here is the int**. The type that the pointer points to is the type of P, which is int*. The address that the pointer points to is the pointer P's own address.
*ptr=&b; *ptr is a pointer, and the result of &b is a pointer, and the two pointers are the same type as the one they are pointing to, so the amp;b assignment to *ptr is no problem.
**ptr=34; *ptr is what PTR points to, and here is a pointer to the pointer to do another * operation, and the result is a variable of type int.



pointer Expression

The final result of an expression if it is a pointer, then the expression is called the pointer expression. Here are some examples of pointer expressions:

Example VI:

int A, B;  
int array[10];
int *pa;
pa=&a; //
int **ptr=&pa; //
*ptr=&b; //

pa++; // This is also a pointer expression.


Example VII:

 char *arr[20 "; 
char **parr=arr;
char *str;
Str=*parr; //*parr is pointer expression
Str =* (Parr+1); //* (parr+1) is a pointer expression str=* (Parr+* (parr+2) is a pointer expression


Because the result of a pointer expression is a pointer, the pointer expression also has four features that the pointer has: the type of pointer, the type that the pointer points to, the memory area that the pointer is pointing to, and the memory that the pointer itself occupies.

Well, when the result pointer of a pointer expression has explicitly had the memory occupied by the pointer itself, the pointer expression is an lvalue, otherwise it is not an lvalue. In example VII, &A is not an lvalue because it does not yet occupy a definite amount of memory. *ptr is an lvalue, because *ptr this pointer has occupied the memory, in fact *ptr is the pointer PA, since PA has in memory has its own position, then *ptr of course also has its own position.

the relationship between arrays and pointers

If you don't understand the statement that declares an array, see the article I posted earlier << how to understand complex type declarations >> for C and C + +. The array name of an array can actually be seen as a pointer. Look at the following example:

Example VIII:

int array[10]={0,1,2,3,4,5,6,7,8,9},value; 
...
...
Value=array[0]; can also be written as: Value=*array;
Value=array[3]; can also be written as: value=* (array+3);
Value=array[4]; can also be written as: value=* (array+4);




In the above example, the array-name array typically represents the array itself, and the type is int [10], but if you think of array as a pointer, it points to the No. 0 cell of the array, the type is int *, and the type to which it refers is the type of the array cell, or int. So it's not surprising that *array equals 0. Similarly, array+3 is a pointer to the 3rd cell of the array, so * (array+3) equals 3. Other and so forth.

Example nine:

Char *str[3]={
"Hello,this is a sample!",
"Hi,good morning. ",
"Hello World"
};
Char s[80];
strcpy (s,str[0]); can also be written as strcpy (S,*STR);
strcpy (s,str[1]); can also be written as strcpy (s,* (str+1));
strcpy (s,str[2]); can also be written as strcpy (s,* (str+2));


In the example above, STR is an array of three cells, each of which is a pointer to a string. With the pointer array name STR as a pointer, it points to the No. 0 element of the array, which is of type char**, and it points to a type of char *. The

*str is also a pointer to the type char*, which is the type char, and the address it points to is a string "Hello,this is a sample!" The address of the first character, which is the address of ' H '. Str+1 is also a pointer to the 1th element of the array, whose type is char**, which is the type of char *.  

* (str+1) is also a pointer to a type of char*, which refers to a type of char, which points to "Hi,good morning." The first character ' H ', and so on. &NBSP;&NBSP

summarizes the array names of arrays. Declares an array of type array[n], the array name arrays has two meanings: first, it represents the entire array, it is of type [n]; second, it is a pointer, the type of the pointer is type*, the type of the pointer is type, that is, the types of the array cells, The memory area that the pointer points to is the No. 0 unit of the array, which occupies a separate memory area, noting that it is different from the memory area occupied by the group No. 0 unit. The value of the pointer cannot be modified, that is, an expression like array++ is wrong. &NBSP

Array names in different expressions arrays can play different roles.   

in Expression sizeof (array), the array name arrays represent the array itself, so the sizeof function detects the size of the entire array.   

in Expression *array, array acts as a pointer, so the result of this expression is the value of cell number No. 0. sizeof (*array) measured the size of the array element.   

Expression array+n (where n=0,1,2, ..... ), array acts as a pointer, so the result of Array+n is a pointer, which is of type type*, and it points to the type, which points to the array nth unit. So sizeof (ARRAY+N) measured the size of the pointer type.  

Example x:   

int array[10];  
int (*ptr) [10];
ptr=&array;


In the example above, PTR is a pointer with the type int (*) [10], and the type he points to is int [10], and we initialize it with the first address of the entire array. In statement Ptr=&array, array represents the array itself.

The function sizeof () is mentioned in this section, so let me ask, does sizeof (the pointer name) measure the size of the pointer itself, or the size of the type that the pointer points to? The answer is the former. For example:

int (*ptr) [ten];  


In a 32-bit program, there are:

sizeof (Int (*) [ten]) = =4  
sizeof (int [10]) = =
sizeof (PTR) = =

In fact, sizeof (the object) measured the size of the object's own type, not the size of any other type.

relationship of pointers and struct types

You can declare a pointer to a struct type object.

Example 11:

struct MYSTRUCT  
{
int A;
int b;
int C;
}

MyStruct ss={; The struct object SS is declared, and the three members of the SS are initialized to 20,30 and 40.
MyStruct *ptr=&ss; // declares a pointer to the struct object ss. It is of the type
mystruct*, the type it points to is mystruct.
int *pstr= (int*) &ss; a pointer to the struct object SS is declared. But its type and the type it points to and PTR are different.

How can I access the three member variables of SS through pointer ptr?

Answer:

ptr->a;  
ptr->b;
ptr->c;


How can I access the three member variables of SS through pointer pstr?
Answer:

*PSTR;// visited member a of the SS.  
* (pstr+1); //
* (pstr+2)//


Oh, although I msvc++6.0 over the above code in my own, but to know that it is not normal to use PSTR to access struct members, in order to explain why it is not normal, let us see how to access the array of cells through pointers:
Example 12:

int array[3]={,37};  

The method by which the pointer PA accesses the array of three cells is:

*PA; // access to Unit No. No. 0  
* (pa+1); //
* (pa+2); //


The format is the same as the format of the informal method of accessing struct members through pointers.

All the C + + compilers, when arranging cells in an array, always store each array cell in a contiguous storage area, with no gaps between the cells and the cells. However, when you store individual members of a structure object, in a certain compilation environment, you may need to align the words or the two words or something else, and you need to add several "padding bytes" between the adjacent two members, which results in a possible number of bytes of space between the members.

Therefore, in example 12, even if *PSTR accesses the first member variable A of the struct object SS, there is no guarantee that * (PSTR+1) will have access to struct member B. Because there may be several padding bytes between member A and member B, it is possible that * (PSTR+1) has access to these padding bytes. This also proves the flexibility of the pointer. If your goal is to see if there are any padding bytes between the members of each structure, hey, that's a good idea.

The correct way to access struct members through pointers should be to use the pointer ptr method in example 12.

the relationship between pointers and functions

A pointer can be declared as a pointer to a function.

int fun1 (char*,int);  
Int (*pfun1) (char*,



int a= (*PFUN1) ("abcdefg",7); //

You can use a pointer as a parameter to a function. In a function call statement, you can use a pointer expression as an argument.

C++study pointer explanation

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.