Detailed discussion on the difference between C + + reference and pointer as formal parameters

  • 2021-12-09 09:48:46
  • OfStack

int n;

int & m = n;

In C + +, there is one more reference declarator that C language does not have & As above, m is the reference of n, and simply speaking, m is the alias of n. They occupy the same position in memory, and do not open up new memory space for m. Any operation for m is the same for n.

For references, there are three rules:

(1) References must be initialized at the same time as they are created (pointers can be initialized at any time).
(2) There can be no NULL reference, and the reference must be associated with a legal storage location (the pointer can be NULL).
(3) 1 Once a reference is initialized, the relationship of the reference cannot be changed (the pointer can change the object it refers to at any time).

If memory space is dynamically requested in a function, different results will be obtained by using pointers and references, such as the following example:


void fun(int* &b){ // Use references as formal parameters 
 b = (int*)malloc(sizeof(int)*3);

 for(int i=0; i<3; i++){
 b[i] = i;
 }
}

If a null pointer of int type is defined in the main function and passed in as arguments, as follows:


int main(){
 int *a = NULL;

 fun(a);

 for(int i=0; i<3; i++){
 cout << a[i] << " ";
 }
 cout << "/n";

 return 0;
}

As a result, functions with pointers will have memory access errors, while functions with references will run normally and output 1 2 3 correctly.

This is because:

1. Although the pointer is passed by address, in fact, a new pointer is defined in the function to point to the same address as the passed pointer. But the two pointers themselves are stored at different addresses in memory as variables, that is to say, they are two different variables, but the contents (that is, the referred addresses) are the same.

2. Memory is dynamically requested for the newly defined pointer in the function, but when the function ends, the life cycle of the requested memory ends, so when returning to the main function, the pointer address and content as arguments do not change. It is still a null pointer, so there is a memory read error when accessing it.

Suppose you write this in the main function:

int *a = (int*)malloc(sizeof(int)*3);

There will be no memory read error, but the output result is still wrong, and the reason is the same.

3. When a reference is passed in as an argument, b in fun function is actually the alias (or nickname) of a in the main function, which is a variable with exactly the same operation, the same address and the same content, so when fun function returns, the operation on b is equally valid for a in the main function.

Look at another example:


int *a = NULL;

char* b = (char*)a;

int *a = NULL;

char* &b = (char*)a ; 

This time is the difference at the compile stage:

Compilation can be done with pointers, but not with references, suggesting that there is an error in type conversion.

From these two examples, we can see that pointers are more flexible and dangerous than references.

Excerpt from "High Quality c + + Programming"

Clause 1: The difference between pointer and reference

Pointers look completely different from references (pointers use the operators' * 'and '- > But they seem to have the same functionality. Pointers and references both allow you to refer to other objects indirectly. How do you decide when to use pointers and when to use references?

First of all, realize that you can't use a reference to a null value under any circumstances. 1 Reference must always point to some object. So if you use a variable and make it point to an object, but the variable may not point to any object at some point, you should declare the variable as a pointer, because then you can assign a null value to the variable. Conversely, if the variable definitely points to an object, for example, your design does not allow the variable to be null, then you can declare the variable as a reference.

PS: References cannot be defined with const, otherwise compilation errors occur, and const can be added before formal parameters to ensure that the variable will not be modified in the function.


Related articles: