Functions and Pointers
Functions and Pointers
FUNCTIONS
Definition
C enables its programmers to break up a program into segments commonly known as
functions. Every function in the program is supposed to perform a well-defined task. Therefore,
the program code of one function is completely insulated from the other functions.
main() calls afunction named func1(). Therefore, main() isknown as the calling function and
func1() is knownas the called function.
TERMINOLOGIES IN FUNCTIONS
A function f that uses another function g is known as the calling function, and g is
known as the called function.
The inputs that a function takes are known as arguments.
When a called function returns some result back to the calling function, it is said to return
that result.
The calling function may or may not pass parameters to the called function. If the called
function accepts arguments, the calling function will pass parameters, else not.
Function declaration is a declaration statement that identifies a function’s name, a list
of arguments that it accepts, and the type of data it returns.
Function definition consists of a function header that identifies the function, followed
by the body of the function containing the executable code for that function.
FUNCTION DECLARATION
The general format for declaring a function that accepts arguments and returns a value as result
can be given as:
return_data_type function_name(data_type variable1, data_type variable2,..);
Here, function_name is a valid name for the function. Naming a function follows the
same rules that are followed while naming variables. A function should have a meaningful name
that must specify the task that the function will perform.
return_data_type specifies the data type of the value that will be returned to the calling
function as a result of the processing performed by the called function.
(data_type variable1, data_type variable2, ...) is a list of variables of specified data types.
These variables are passed from the calling function to the called function. They are also known
as arguments or parameters that the called function accepts to perform its task .
Function Definition
When a function is defined, space is allocated for that function in the memory. A function
definition
comprises of two parts:
Function header
Function body
The syntax of a function definition can be given as:
return_data_type function_name(data_type variable1, data_type variable2,..)
{
.............
statements
.............
return(variable);
}
The number of arguments and the order of arguments in the function header must be
the same as that given in the function declaration statement.
return_data_type function_name(data_type variable1, data_type variable2,...) is known
as the function header, the rest of the portion comprising of program statements within the curly
brackets { } is the function body which contains the code to perform the specific task.
The function header is same as the function declaration. The only difference between
the two is that a function header is not followed by a semi-colon.
FUNCTION CALL
The function call statement invokes the function. When a function is invoked, the
compiler jumps to the called function to execute the statements that are a part of that function.
Once the called function is executed, the program control passes back to the calling function. A
function call statement has the following syntax:
function_name(variable1, variable2, ...);
If the return type of the function is not void, then the value returned by the called function
may be assigned to some variable as given below.
variable_name = function_name(variable1, variable2, ...);
Eg:// program to find whether a number is even or odd using functions.
#include <stdio.h>
int evenodd(int); //FUNCTION DECLARATION
int main()
{
int num, flag;
printf("\n Enter the number : ");
scanf("%d", &num);
flag = evenodd(num); //FUNCTION CALL
if (flag == 1)
printf("\n %d is EVEN", num);
else
printf("\n %d is ODD", num);
return 0;
}
int evenodd(int a) // FUNCTION HEADER
{
// FUNCTION BODY
if(a%2 == 0)
return 1;
else
retun 0;
}
Output
Enter the number : 78
78 is EVEN
PASSING PARAMETERS TO FUNCTIONS
There are two ways in which arguments or parameters can be passed to the called
function.
Call by value The values of the variables are passed by the calling function to the called
function.
Call by reference The addresses of the variables are passed by the calling function to the
called function.
Call by Value
In this method, the called function creates new variables to store the value of the
arguments passedto it. Therefore, the called function uses a copy of the actual arguments to
perform its intended task.
If the called function is supposed to modify the value of the parameters passed to it, then
the change will be reflected only in the called function. In the calling function, no change will be
made to the value of the variables. This is because all the changes are made to the copy of the
variables and not to the actual variables.
Eg://Program for call by value
#include <stdio.h>
void add(int n);
int main()
{
int num = 2;
printf("\n The value of num before calling the function = %d", num);
add(num);
printf("\n The value of num after calling the function = %d", num);
return 0;
}
void add(int n)
{
n = n + 10;
printf("\n The value of num in the called function = %d", n);
}
Output
The value of num before calling the function = 2
The value of num in the called function = 12
The value of num after calling the function = 2
Pros and cons
The biggest advantage of using the call-by-value technique is that arguments can be
passed as variables, literals, or expressions.
Iits main drawback is that copying data consumes additionalstorage space. In addition, it
can take a lot of time to copy, thereby resulting in performance penalty,especially if the function
is called many times.
CALL BY REFERENCE
In this method, the function parameters as references rather than normal variables.
When this is done, any changes made by the function to the arguments it received are also visible
in the calling function.To indicate that an argument is passed using call by reference, an asterisk
(*) is placed afterthe type in the parameter list.
Hence, in the call-by-reference method, a function receives an implicit reference to the
argument, rather than a copy of its value. Therefore, the function can modify the value of the
variable and that change will be reflected in the calling function as well.
Eg//Program for Call by reference
#include <stdio.h>
void add(int *);
int main()
{
int num = 2;
printf("\n The value of num before calling the function = %d", num);
add(&num);
printf("\n The value of num after calling the function = %d", num);
return 0;
}
void add(int *n)
Introduction to C 33
{
*n = *n + 10;
printf("\n The value of num in the called function = %d", *n);
}
Output
The value of num before calling the function = 2
The value of num in the called function = 12
The value of num after calling the function = 12
Advantages
1.Since arguments are not copied into the new variables, it provides greater time and
spaceefficiency.
2.The function can change the value of the argument and the change is reflected in the calling
function.
3.A function can return only one value. In case we need to return multiple values, we can pass
those arguments by reference, so that the modified values are visible in the calling function.
Disadvantages
if inadvertent changes are caused to variables in called function then these changes would be
reflected in calling function as original values would have been overwritten.
Eg://This function swaps the value of two variables
#include <stdio.h>
void swap_call_val(int, int);
void swap_call_ref(int *, int *);
int main()
{
int a=1, b=2, c=3, d=4;
printf("\n In main(), a = %d and b = %d", a, b);
swap_call_val(a, b);
printf("\n In main(), a = %d and b = %d", a, b);
printf("\n\n In main(), c = %d and d = %d", c, d);
swap_call_ref(&c, &d);
printf("\n In main(), c = %d and d = %d", c, d);
return 0;
}
void swap_call_val(int a, int b)
{
int temp;
temp = a;
a = b;
b = temp;
printf("\n In function (Call By Value Method) – a = %d and b = %d", a, b);
}
void swap_call_ref(int *c, int *d)
{
int temp;
temp = *c;
*c = *d;
*d = temp;
printf("\n In function (Call By Reference Method) – c = %d and d = %d", *c, *d);
}
Output
In main(), a = 1 and b = 2
In function (Call By Value Method) – a = 2 and b = 1
In main(), a = 1 and b = 2
In main(), c = 3 and d = 4
In function (Call By Reference Method) – c = 4 and d = 3
In main(), c = 4 and d = 3
RECURSIVE FUNCTION
A recursive function is defined as a function that calls itself to solve a smaller version of
its task until a final call is made which does not require a call to itself. Every recursive solution
has two major cases. They are
Base case, in which the problem is simple enough to be solved directly without making
anyfurther calls to the same function.
Recursive case, in which first the problem at hand is divided into simpler sub-parts.
Second the function calls itself but with sub-parts of the problem obtained in the first
step. Third, the result is obtained by combining the solutions of simpler sub-parts.
Indirect Recursion
A function is said to be indirectly recursive if it contains a call to another function which
ultimately calls it.
Tail Recursion
A recursive function is said to be tail recursive if no operationsare pending to be
performed when the recursive function returnsto its caller. when the called function returns, the
returned value is immediately returned from the calling function. Tail recursive functions are
highly desirable because they are much more efficient to use as the amount of information that
has to be stored on the system stack is independent of the number of recursive calls.
Advantages
Recursive solutions often tend to be shorter and simpler than non-recursive ones.
Code is clearer and easier to use.
Recursion works similar to the original formula to solve a problem.
Recursion follows a divide and conquer technique to solve problems.
disadvantages
Recursion is implemented using system stack. If the stack space on the system is limited,
recursion to a deeper level will be difficult to implement.
Aborting a recursive program in midstream can be a very slow process.
Using a recursive function takes more memory and time to execute as compared to its
nonrecursivecounterpart.
It is difficult to find bugs, particularly while using global variables.
Eg:/./Program to do binary search using recursion
#include<stdio.h>
#include<stdlib.h>
#define size 10
int binsearch(int[], int, int, int);
int main() {
int num, i, key, position;
int low, high, list[size];
printf("\nEnter the total number of elements");
scanf("%d", &num);
printf("\nEnter the elements of list :");
for (i = 0; i < num; i++) {
scanf("%d", &list[i]);
}
low = 0;
high = num - 1;
printf("\nEnter element to be searched : ");
scanf("%d", &key);
position = binsearch(list, key, low, high);
if (position != -1) {
printf("\nNumber present at %d", (position + 1));
} else
printf("\n The number is not present in the list");
return (0);
}
// Binary Search function
int binsearch(int a[], int x, int low, int high) {
int mid;
if (low > high)
return -1;
mid = (low + high) / 2;
if (x == a[mid]) {
return (mid);
} else if (x < a[mid]) {
binsearch(a, x, low, mid - 1);
} else {
binsearch(a, x, mid + 1, high);
}
}
Output :
Enter the total number of elements : 5
Enter the elements of list : 11 22 33 44 55
Enter element to be searched : 33
Number present at 3
2. POINTERS
A pointer is a variable that contains the memory location of another variable.
Declaring Pointer Variables
The general syntax of declaring pointer variables can be given as below.
SYNTAX: data_type *ptr_name;
Here, data_type is the data type of the value that the pointer will point to. For example,
Eg: int x= 10;
int *ptr;
ptr = &x;
Eg//Program using pointers
:#include <stdio.h>
int main()
{
int num, *pnum;
pnum = #
printf("\n Enter the number : ");
scanf("%d", &num);
printf("\n The number that was entered is : %d", *pnum);
return 0;
}
Output
Enter the number : 10
The number that was entered is : 10
THE POINTER OPERATORS:
There are two pointer operators :
1. value at address operator ( * )
2. address of operator ( & )
Value at address operator ( * )
The * is a unary operator. It gives the value stored at a particular address. The ‘value at address’
operator is also called ‘indirection’ operator.
q = *m;
if m contains the memory address of the variable count, then preceding assignment statement can
places the value of count into q.
Address of operator ( & )
The & is a unary operator that returns the memory address of its operand.
m = & count;
The preceding assignment statement can be “The memory address of the variable count is places
into m”.
POINTER ARITHMETIC
There are four arithmetic operators that can be used on pointers: ++, --, +, and
–
Valid Pointer Arithmetic Operations Invalid Pointer Arithmetic Operations
Adding a number to pointer. Addition of two pointers.
Subtracting a number form a Division of two pointers.
pointer. Multiplication of two pointers
Incrementing a pointer.
Decrementing a pointer.
Subtracting two pointers.
Comparison on two pointers
OUTPUT:
#include <stdio.h> p1 = 2680016
int main() p2 = 2680012
*p1+*p2 = 15
{ p1-p2 = 1
int m = 5, n = 10, q = 0; p1++ = 2680020
int *p1; p2-- = 2680008
int *p2;
int *p3;
p1 = &m; //printing the address of m
p2 = &n; //printing the address of n
printf("p1 = %d\n", p1);
printf("p2 = %d\n", p2);
q = *p1+*p2;
printf("*p1+*p2 = %d\n", q);//point 1
p3 = p1-p2;
printf("p1 - p2 = %d\n", p3); //point 2
p1++;
printf("p1++ = %d\n", p1); //point 3
p2--;
printf("p2-- = %d\n", p2); //point 4
//Below line will give ERROR
printf("p1+p2 = %d\n", p1+p2); //point 5
return 0;
}
NULL POINTER
null pointer which is a special pointer value and does not point to any value. This means
that a null pointer does not point to any valid memory address.
int *ptr = NULL;
Eg:Write a program to add two integers using pointers and functions.
#include <stdio.h>
void sum (int*, int*, int*);
int main()
{
int num1, num2, total;
printf("\n Enter the first number : ");
scanf("%d", &num1);
printf("\n Enter the second number : ");
scanf("%d", &num2);
sum(&num1, &num2, &total);
printf("\n Total = %d", total);
return 0;
}
void sum (int *a, int *b, int *t)
{
*t = *a + *b;
}
Output
Enter the first number : 23
Enter the second number : 34
Total = 57
Pointers and Arrays :
Syntax:int *ptr;
ptr = &arr[0];
Here, ptr is made to point to the first element of the array.
Eg:// program to display an array of given numbers.
#include <stdio.h>
int main()
{ Output
int arr[]={1,2,3,4,5,6,7,8,9}; 123456789
int *ptr1, *ptr2;
ptr1 = arr;
ptr2 = &arr[8];
while(ptr1<=ptr2)
{
printf("%d", *ptr1);
ptr1++;
}
return 0;
}
Array of ‘Pointers:
An array of pointers can be declared as Syntax: datatype *array_name[size];
Eg:int *ptr[10];
The above statement declares an array of 10 pointers where each of the pointer points to an
integer
variable.
Eg 1: OUTPUT:4
int main()
{
int *ptr[10];
int p = 1, q = 2, r = 3, s = 4, t = 5;
ptr[0] = &p;
ptr[1] = &q;
ptr[2] = &r;
ptr[3] = &s;
ptr[4] = &t;
printf("\n %d", *ptr[3]);
return 0;
}
Eg2://Program on Array of Pointers
int main()
Output
{
101
int arr1[]={1,2,3,4,5};
int arr2[]={0,2,4,6,8};
int arr3[]={1,3,5,7,9};
int *parr[3] = {arr1, arr2, arr3};
int i;
for(i = 0;i<3;i++)
printf(«%d», *parr[i]);
return 0;
}
Applications of Pointers
Pointers are used to pass information back and forth between functions.
Pointers enable the programmers to return multiple data items from a function via
function arguments.
Pointers provide an alternate way to access the individual elements of an array.
Pointers are used to pass arrays and strings as function arguments.
Pointers are used to create complex data structures, such as trees, linked lists, linked
stacks,linked queues, and graphs.
return 0;
}