Passing Arguments by Value and by Reference

Figure 6.19 compares pass-by-value and pass-by-reference with reference parameters. The “styles” of the arguments in the calls to function squareByValue and function squareByReference are identical—both variables are simply mentioned by name in the function calls. Without checking the function prototypes or function definitions, it isn’t possible to tell from the calls alone whether either function can modify its arguments. Because function prototypes are mandatory, the compiler has no trouble resolving the ambiguity.


 1   // Fig. 6.19: fig06_19.cpp
 2   // Passing arguments by value and by reference.
 3   #include <iostream>
 4   using namespace std;
 5
 6   int squareByValue( int ); // function prototype (value pass)           
 7   void squareByReference( int & ); // function prototype (reference pass)
 8
 9   int main()
10   {
11      int x = 2; // value to square using squareByValue
12      int z = 4; // value to square using squareByReference
13
14      // demonstrate squareByValue
15      cout << "x = " << x << " before squareByValue ";
16      cout << "Value returned by squareByValue: "
17         << squareByValue( x ) << endl;
18      cout << "x = " << x << " after squareByValue " << endl;
19
20      // demonstrate squareByReference
21      cout << "z = " << z << " before squareByReference" << endl;
22      squareByReference( z );
23      cout << "z = " << z << " after squareByReference" << endl;
24   } // end main
25
26   // squareByValue multiplies number by itself, stores the     
27   // result in number and returns the new value of number      
28   int squareByValue( int number )                              
29   {                                                            
30      return number *= number; // caller's argument not modified
31   } // end function squareByValue                              
32
33   // squareByReference multiplies numberRef by itself and stores the result
34   // in the variable to which numberRef refers in function main            
35   void squareByReference( int &numberRef )                                 
36   {                                                                        
37      numberRef *= numberRef; // caller's argument modified                 
38   } // end function squareByReference                                      


x = 2 before squareByValue
Value returned by squareByValue: 4
x = 2 after squareByValue

z = 4 before squareByReference
z = 16 after squareByReference


Fig. 6.19. Passing arguments by value and by reference.


Image Common Programming Error 6.8

Because reference parameters are mentioned only by name in the body of the called function, you might inadvertently treat reference parameters as pass-by-value parameters. This can cause unexpected side effects if the original variables are changed by the function.


Chapter 8 discusses pointers; pointers enable an alternate form of pass-by-reference in which the style of the call clearly indicates pass-by-reference (and the potential for modifying the caller’s arguments).


Image Performance Tip 6.7

For passing large objects, use a constant reference parameter to simulate the appearance and security of pass-by-value and avoid the overhead of passing a copy of the large object.


To specify that a reference should not be allowed to modify the argument, place the const qualifier before the type specifier in the parameter declaration. Note the placement of & in function squareByReference’s parameter list (line 35, Fig. 6.19). Some C++ programmers prefer to write the equivalent form int& numberRef.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.220.163.91