Parameter Passing in C++ Functions

In a C++ program, calling a function requires passing it arguments. Apart from an empty parameter list (void), parameter passing comes in two kinds: pass by reference and pass by value.

Pass by Reference and Pass by Value

When a parameter is a reference type, we say the corresponding argument is passed by reference, or that the function is called by reference. Like any other reference, a reference parameter is an alias for the object it is bound to; that is, a reference parameter is an alias for its corresponding argument.

void reset(int &i){
		i=0;   //the value of i will change
}

When a non-reference parameter is initialized, the initial value is copied into the variable: the value of the argument is copied into the parameter, and the parameter and the argument are two independent objects. We say such an argument is passed by value, or that the function is called by value.

void reset(int i){
		i=0;   //the value of the argument i will not change
}

Note that if you pass in a pointer object, you can change the value of the object it points to through the pointer. This is very common in C, but in C++ this kind of requirement should be implemented using pass by reference.

void reset(int *i){
		*i=0;   //the value of the object pointed to by pointer i will likewise change
}

In addition, when passing in a literal constant, if the literal constant is large, it is best to avoid the copying involved in pass by value and use pass by reference instead. Note that in this case the reference parameter must be defined as a low-level const, because you cannot pass a literal to a non-const reference parameter.

string::size_type find_char(string &s,char c);
//the first parameter of this function should be const string &s, otherwise a compile error will occur

Functions with a Variable Number of Parameters

To write a function that can handle a varying number of arguments, the new C++11 standard provides two main approaches: if all the arguments have the same type, you can pass a standard library type named initializer_list; if the arguments have different types, you can write a special kind of function, the so-called variadic template, which we will not cover in detail here.

The following form writes a function that prints error messages so that it can operate on a variable number of arguments.

void error_msg(initializer_list<string> i1){
	for(auto beg=i1.begin();beg!=i1.end();beg++){
		cout<<*beg<<" ";
	}
	cout<<endl;
}

Default Argument Initialization of Parameters

Some functions have a parameter that is given the same value across many of the function’s calls. In this case, we call this repeatedly occurring value the function’s default argument. Note that once a parameter is given a default value, all the parameters that follow it must also have default values.

typedef string::size_type sz;
//define default values for the function arguments in the declaration
string screen(sz ht=24,sz wid=80,char backgrnd=' ');
string window;
window=screen();	//equivalent to screen(24,80,' ')

For function declarations, the usual convention is to place them in a header file and declare each function only once, though multiple declarations are also allowed. Note, however, that within a given scope a parameter can be given a default argument only once.

string screen(sz,sz,char='*');	//error, redeclaration