Feb 5, 2020

Functions in C - Passing Values between Functions

            Unit IV (Contd…..)


          Passing arguments, calling functions.  

          Passing Values between Functions

Consider the following program. In this program, in main( ) we receive the values of a, b and c through the keyboard and then output the sum of a, b and c. However, the calculation of sum is done in a different function called calsum( ). If sum is to be calculated in calsum( ) and values of a, b and c are received in main( ), then we must pass on these values to calsum( ), and once calsum( ) calculates the sum we must return it from calsum( ) back to main( ).

/* Sending and receiving values between functions */
main( )
{
int a, b, c, sum ;
printf ( "\nEnter any three numbers " ) ;
scanf ( "%d %d %d", &a, &b, &c ) ;
sum = calsum ( a, b, c ) ;
printf ( "\nSum = %d", sum ) ;
}
calsum ( x, y, z )
int x, y, z ;
{
int d ;
d = x + y + z ;
return ( d ) ;
}
And here is the output...
Enter any three numbers 10 20 30
Sum = 60

There are a number of things to note about this program:

(a)  In this program, from the function main( ) the values of a, b and c are
passed on to the function calsum( ), by making a call to the function
     calsum( ) and mentioning a, b and c in the parentheses:

sum = calsum ( a, b, c ) ;

     In the calsum( ) function these values get collected in three variables x, y   
     and z:

calsum ( x, y, z )
int x, y, z ;

(b) The variables a, b and c are called ‘actual arguments’, whereas the
variables x, y and z are called ‘formal arguments’. Any number of arguments can be passed to a function being called. However, the type, order and number of the actual and formal arguments must always be same.
Instead of using different variable names x, y and z, we could have used the same variable names a, b and c. But the compiler would still treat them as different variables since they are in different functions.

(c)  There are two methods of declaring the formal arguments. The one that
we have used in our program is known as Kernighan and Ritchie (or just K & R) method.

calsum ( x, y, z )
int x, y, z ;

Another method is,

calsum ( int x, int y, int z )

This method is called ANSI method and is more commonly used these days.

(d) In the earlier programs the moment closing brace ( } ) of the called
function was encountered the control returned to the calling function. No separate return statement was necessary to send back the control.
This approach is fine if the called function is not going to return any meaningful value to the calling function. In the above program, however, we want to return the sum of x, y and z. Therefore, it is necessary to use the return statement.

The return statement serves two purposes:

(1)  On executing the return statement it immediately transfers the control
back to the calling program.

(2)  It returns the value present in the parentheses after return, to the calling
program. In the above program the value of sum of three numbers is being returned.

(e)  There is no restriction on the number of return statements that may be
present in a function. Also, the return statement need not always be present at the end of the called function. The following program illustrates these facts.
fun( )
{
char ch ;
printf ( "\nEnter any alphabet " ) ;
scanf ( "%c", &ch ) ;
if ( ch >= 65 && ch <= 90 )
return ( ch ) ;
else
return ( ch + 32 ) ;
}

In this function different return statements will be executed depending on whether ch is capital or not.

(f) Whenever the control returns from a function some value is definitely 
     returned. If a meaningful value is returned then it should be accepted in the 
     calling program by equating the called function to some variable. 
     
    For example:

sum = calsum ( a, b, c ) ;

(g) All the following are valid return statements.

return ( a ) ;
return ( 23 ) ;
return ( 12.34 ) ;
return ;

In the last statement a garbage value is returned to the calling function since we are not returning any specific value. Note that in this case the parentheses after return are dropped.

(h) If we want that a called function should not return any value, in that case,
     we must mention so by using the keyword void as shown below.

void display( )
{
printf ( "\nHeads I win..." ) ;
printf ( "\nTails you lose" ) ;
}


(i)     A function can return only one value at a time. Thus, the following
statements are invalid.

return ( a, b ) ;
return ( x, 12 ) ;

There is a way to get around this limitation, which would be discussed later in this chapter when we learn pointers.

(j)     If the value of a formal argument is changed in the called function, the
corresponding change does not take place in the calling function. 

For example:

main( )
{
int a = 30 ;
fun ( a ) ;
printf ( "\n%d", a ) ;
}
fun ( int b )
{
b = 60 ;
printf ( "\n%d", b ) ;
}
The output of the above program would be:

60
30

Thus, even though the value of b is changed in fun( ), the value of a in
main( ) remains unchanged. This means that when values are passed to a called function the values present in actual arguments are not physically moved to the formal arguments; just a photocopy of values in actual argument is made into formal arguments.


Call by Value and Call by Reference

While calling a function, there are two ways that arguments can be passed to a function:

·        Call by Value
·        Call by Reference

           Function call by value

The call by value method of passing arguments to a function copies the actual value of an argument into the formal parameter of the function. In this case, changes made to the parameter inside the function have no effect on the argument.

By default, C programming language uses call by value method to pass arguments. In general, this means that code within a function cannot alter the arguments used to call the function. Consider the function swap() definition as follows.

/* function definition to swap the values */
void swap(int x, int y)
{
int temp;
temp = x; /* save the value of x */
x = y; /* put y into x */
y = temp; /* put x into y */
return;
}

Now, let us call the function swap() by passing actual values as in the following example:

#include <stdio.h>
/* function declaration */
void swap(int x, int y);
int main ()
{
/* local variable definition */
int a = 100;
int b = 200;
printf("Before swap, value of a : %d\n", a );
printf("Before swap, value of b : %d\n", b );
/* calling a function to swap the values */
swap(a, b);
printf("After swap, value of a : %d\n", a );
printf("After swap, value of b : %d\n", b );
return 0;
}
Let us put above code in a single C file, compile and execute it, it will produce the following result:

Before swap, value of a :100
Before swap, value of b :200
After swap, value of a :100
After swap, value of b :200

          Which shows that there is no change in the values though they had been 
          changed inside the function.

          Function call by reference

The call by reference method of passing arguments to a function copies the address of an argument into the formal parameter. Inside the function, the address is used to access the actual argument used in the call. This means that changes made to the parameter affect the passed argument.
To pass the value by reference, argument pointers are passed to the functions just like any other value. So accordingly you need to declare the function parameters as pointer types as in the following function swap(), which exchanges the values of the two integer variables pointed to by its arguments.

/* function definition to swap the values */
void swap(int *x, int *y)
{
int temp;
temp = *x; /* save the value at address x */
*x = *y; /* put y into x */
*y = temp; /* put x into y */
return;
}
Let us call the function swap() by passing values by reference as in the following example:

#include <stdio.h>
/* function declaration */
void swap(int *x, int *y);
int main ()
{
/* local variable definition */
int a = 100;
int b = 200;
printf("Before swap, value of a : %d\n", a );
printf("Before swap, value of b : %d\n", b );
/* calling a function to swap the values.
* &a indicates pointer to a ie. address of variable a and
* &b indicates pointer to b ie. address of variable b.
*/
swap(&a, &b);
printf("After swap, value of a : %d\n", a );
printf("After swap, value of b : %d\n", b );
return 0;
}
Let us put above code in a single C file, compile and execute it, it will produce the following result:

Before swap, value of a :100
Before swap, value of b :200
After swap, value of a :100
After swap, value of b :200

Which shows that there is no change in the values though they had been changed inside the function.

No comments:

Post a Comment