Sie sind auf Seite 1von 4

Procedure Calls:

Communication between the calling and the called procedures via parameters. Parameters are
passed using different mechanisms. Parameter passing is the mechanism of substitution of formal
parameters by actual parameters. Execution of the body of the procedures is the replacement of
procedure invocation with procedure body Parameter passing mechanisms: Call-by-value:
evaluate the actual parameters, assign them to corresponding formal parameters, execute the
body of the procedure
int p(int x) {
x=x+1;
return x ;
}
with call-by-value, an expression y = p(5+3) is executed as follows:
evaluate 5+3 = 8, call p with 8, assign 8 to x, increment x, return x which is assigned to y.
Call-by-reference: evaluate actual parameters, which must have l-values assign these l-values to
l-values of corresponding formal parameters, execute the body.
Call-by-reference is explicit in C, whereas implicit in C++; for the above program, in C, one has
to write it as
int p (int *x) {
*x = *x + 1 ;
return *x ;
}
...
int z ;
y = p (&z) ;
Call-by-value-result: works like call by value but in addition, formal parameters are assigned to
actual parameters at the end of procedure with call-by-value-result (which C doesn't support hence the following is pseudo-code),
void p (int x, int y) {
x=x+1;
y=y+1;
}
...
int a = 3 ;
p (a, a) ;
after the call, a will have the value 4, whereas with call-by-reference, a will have the value 5.
the following is the equivalent of call-by-value-result call above:
x=a;
y=a;
x=a;
1

x=x+1;
y=y+1;
a=x;
a=y;
thus, at the end, a = 4.
Call-By-Value
-------------Preprocessing:
a) create a block whose body is that of the procedure being called
b) introduce declarations for each formal parameter, and initialize them with the values of the
actual parameters
Inline:
Subsitute the block (obtained by the above preprocessing step) in the place of procedure
invocation statement.
Example:
int z;
void p(int x) {
z = 2*x;
}
main() {
int y;
p(y);
}
Replacing the invocation p(y) in the above manner yields the following main program:
main() {
int y;
{
/* Created a new block corresponding to body of f */
int x = y; /* Assign acual parameter to formal parameters */
z = 2*x; /* inline body of p as usual. */
}
Fine print: We need to ensure that the variables declared in the body of the procedure do not
clash with the variable names visible at the invocation
point. If they do, the variables in the procedure body whould be renamed to avoid the clash.

Call-By-Value-Result
---------------------In addition to the preprocessing step in CBV, add assignment statements to the end of the block
that assigns formal parameter values to actual parameters.
Example: For the above program, we will get:
main() {
int y;
{ /* Created a new block corresponding to body of f */
int x = y; /* Assign acual parameter to formal parameters */
z = 2*x; /* inline body of p as usual. */
y = x; /* assign formal parameter value back to actual parameters */
}
Call-by-Name
------------Preprocessing: substitute formal parameters in the body of the procedure by actual parameter
expressions. If any of the actual parameters have the same name as a local variable used in the
called procedure body, then the local variable will first be renamed before the substitution.
Inline: Substitute the invocation expression with the modified procedure body.
Example: In the above example, we will get:
main() {
int y;
{
z = 2*y;
}
}
Macros
-------Macros work very much like call-by-name parameter passing, and has some
of its problems described below. In addition, macros suffer from the fact
they do not support the concept of local variables. This means that
possible name clashes between actual parameters and variables in the
body of the macro will lead to unexpected results. For instance,
given the macro:
#define sixtimes(y) { int z; z = 2*y; y = 3*z;} and the program:
3

main() {
int x = 5, z = 3;
sixtimes(z);
}
After macro substitution, we get the program:
main() {
int x = 5, z = 3;
{
int z;
z = 2*z;
z = 3*z;
}
}
which is different from what we would have got with CBN parameter
passing. In particular, the name confusion between the local variable
z and the actual parameter z would have been avoided, leading to the
following result:
main() {
int x = 5, z = 3;
{
int z1; /* local variable renamed to avoid clash with actual parameter */
z1 = 2*z;
z = 3*z1;
}
}

Das könnte Ihnen auch gefallen