Monday 31 December 2018

STORAGE CLASSES


STORAGE CLASSES 
Every variable In C language has a powerful characteristic called Storage Class.  There are 3 basic places in a c-program where variables will be declared:
  1. Inside the function
  2. in the definition of function
  3. Outside of all functions.
These variables are called as local variables, formal variables and global variables.

Local Variables:
A variable declared inside a function is called as local variables. A local variable will be visible to the function in which it is declared.

Global Variables:
A variable declared in the global variable section are called as global variables. A global variable can be used anywhere in the program. The proper place of declaration of global variable is at the beginning of the main program.

#include<stdio.h>
#include<conio.h>
int a=10;               //      global variable can be accessed from
anywhere in the program

void main( )
{
                   clrscr();
{
                             int x=20;                //local variable can be accessed
with in the function or within the block.
                             printf(“%d%d”,a,x);
                   }
printf(“\n%d”,a);
printf(“\n%d,%d”,a,x);     //error ‘x’ not accessible
}
Output:
10 20
10

A variable defined in a block can be accessed within the block and all its inner blocks. It is called as scope of variable.

While defining a variable we mentioned only its data type. To fully define a variable we need to mention not only its data type, but also its storage class. If we don’t specify it the compiler will assume a default storage class depending on the context where variable is defined.

In ‘C there are 4 types of storage classes.
  • auto
  • static
  • register
  • extern

The storage class tells us 4 things:
  • Default initial value: what will be the default initial value of the variable as soon as it is defined
  • Location: where the variable would be stored
  • Scope: where the variable can be accessed.
  • Life: How long the memory remains reserved for the variable.

By default the storage class for any variable is auto


Auto
Static
Register
Extern
Default initial value
Garbage
0
Garbage
0
Location
RAM
RAM
CPU Registers
RAM
Scope
Local to the block where the variable is defined
Local to the block where the variable is defined
Local to the block where the variable is defined
Entire Program
Life
As long as the control is within the block where  the variable is defined
As long as the program is under execution
As long as the control is within the block where  the variable is defined
As long as the program is under execution

/* Auto Storage Class */

#include<stdio.h>
#include<conio.h>
void fun()
{
          int a=10;
                   printf("%d\n",a);
          a++;
}
void main()
{
          fun();
          fun();
          fun();
}
Output:
10
10
10
Here the storage class is auto be default. Auto variable life is as long as the control is within the block where the variable is defined. Whenever the statement, int a=10; gets executed, memory gets allocated to ‘a’ and the location is initialized with 10. Whenever the control comes out of the fun( ) function block, the variable ‘a’ dies, i.e., memory allocated gets released and hence the output.

/* Static Storage Class */

#include<stdio.h>
#include<conio.h>
void fun()
{
          static int a=10;
                   printf("%d\n",a);
          a++;
}
void main()
{
          fun();
          fun();
          fun();
}
Output:
10
11
12

Static variable life is as long as the program is under the execution. These variables gets memory allocated as soon as the program gets loaded into memory and memory gets deallocated just before the termination of the program from the memory.  
          Static int a=10;
gets executed only once and when the control enters the fun () for the next time the line gets ignored so it has the value what is has the last time. Its value persists between different function calls, and hence the output. These are local to the block.


/* register storage class */

These variables are accessed much quickly than other variables as they reside in the registers of the microprocessor. Because of the limited size and number of registers available, few variables can actually be put in registers. If the compiler does not allocate a machine register for a variable, then the variable is treated as auto. We cannot use register for all types of variables (for ex., long, float, double) because the CPU registers are usually 16-bit registers. As these are declared in registers these cannot be referred by the pointer variable. The variables of most frequent use should only be of register type.

#include<stdio.h>
#include<conio.h>
void main()
{
          register int i;
          for (i=1;i<=100;i++)
                   printf("Hai");
}

Here the i gets accessed around 100 times so if it is made to reside in cpu registers program execution will be fast.
Output:
HaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHaiHai

/* extern storage class */

When there is a need for a variable to be accessed in all the functions in a program then the external variables serve the purpose.
#include<stdio.h>
#include<conio.h>
int a;  /* by default a is 0 */
void main()
{
          a=a+1;
          clrscr();
          printf("%d\t",a);
          fun1();
          fun2();
          fun3();
          fun4();
          getch();
}
fun1()
{
          a=a+10;
          printf("%d\t",a);
}
fun2()
{
          a=a+5;
          printf("%d\t",a);
}
fun3()
{
          a=a-2;
          printf("%d\t",a);
}
fun4()
{
          a=a+8;
          printf("%d\t",a);
}

Output:
1       11      16      14      22 

Saturday 29 December 2018

FUNCTIONS


FUNCTIONS

A function is a self-contained block of statements that can be called for any number of times. A function is a collection of logically related instructions which performs a specific task.
Some of the predefined functions are: printf( ), scanf( ), strlen( ), strcpy( ) etc.
Here the set of instructions are specified for the above functions by C. We are directly using these functions without having the knowledge of internal code for the above functions. We can even call those functions any number of times. We can also define our own user-defined functions. By using functions there are some advantages. They are:
  1. Functions are used for reusability of code
  2. We can save time
  3. Length of the program can be reduced by using functions
  4. Program development becomes easy
  5. Code-reusability increases
  6. Code sharing becomes possible
Syntax:         returntype function_name(list of arguments)
                      {
                                   Executable statements;
                                   Return statements;
                      }
Types of Functions
Functions are of 2 types:-
Library functions: The functions which are developed by c-developer
Ex: printf( ), scanf( ), clrscr( )
User-defined functions: The functions which are defined by the user.
Ex: any userdefined name, main( )
main( ) is a user-defined function but it act as a predefined/library function.

/* Creating a user-defined function */

void fun( )                       //called function
{
          printf(“Hello”);       //calling the predefined printf function
          printf(“welcome to functions”); //function definition
}
void main( )
{
          fun( );                    //calling the user defined function
}


Function definition:  it contains the return type, name, parameters list and body.
Function calling: Transferring control from one function to another function.
Calling function: A function which calls another function is called as calling function. In the above example, fun( ), main( ), printf( ) are all calling functions
Called function: A function which gets called are called as called functions. Ex: fun( ) is a called function which was called by main( ).

Declaration of a function:
Every function has its declaration and function definition. Function declaration contains returntype, no of arguments, and function name.
Syntax:       return type function_name(args list)
Ex:              int square(int no);
                   void temp(float f)
in the above functions if you declare return type as void then we need not return any value from that function, if we mention return type other than void we have to return the value from that function. In the above example we have used int as return type, then we have to return an integer number from the square function.

/* Returning a value from a function */
#include<stdio.h>
void main( )
{
          int a=5,b=6,c;                 actual arguments
          c=sum(a,b);           //      calling function sum by passing a and b as arguments
}
int sum(int a,int b)          //called function
{                                               formal arguments
          int c;
          c=a+b;                    // function definition
          return c;
}                                      here the return type is int we are returning the
int value

A function can return only one value at a time.
Arguments can also be called as parameters. Parameters are used to communicate data between the calling & called functions.
Actual arguments:  the variables or the arguments used in the calling function are called as actual arguments.
Formal arguments:  the variables or the arguments used in the called function are called as formal arguments.
The names of actual & formal arguments are may or may not the same. Even though the names are same the “C” compiler treats them as different variables.

Function Prototype
Prototypes are which tells the behaviour of the function. The prototype of a function specifies its return type, name and the type of arguments.

Types of functions
A function, depending on whether arguments are present or not and whether a value is returned or not, may belong to one of the following categories:
  • with no arguments and with no return value
  • with no arguments and with return value
  • with arguments and with no return value
  • with arguments and with return value.

With no arguments and with no return value
These type of functions do not receive any values from the calling function no they send any data to the calling function. So there is no communication between the calling and called function are only program control will be transferred.
/* function with no args and no return values */
#include<stdio.h>
void main()
{
          void message(); /* function declaration */
          clrscr();
          printf("control back to main");
          message();    //function with no arguments
          printf("control back to main\n");
}
void message()
{
          printf("\ncontrol is in message function\n");
          //function with no return values
}
Output:
control back to main
control is in message function
control back to main

With no arguments and with return value
These type of functions does not receive any values from calling function but returns some value to the calling function.
/* function with no args and with return values */
#include<stdio.h>
void main()
{
          int sum;
          clrscr();
          sum=cal_sum();     //function with no arguments
                                      //return value from cal_sum( ) i.e., s will be
    stored in sum
printf("sum of first ten natural nos is %d",sum);
}
int cal_sum()
{
          int i,s=0;
          for(i=1;i<10;i++)
                   s=s+i;
          return s;                //function with return value
}
Output:
sum of first ten natural nos is 45

With arguments and with no return value
These type of functions send values from calling function to the called function but called function will not return any value to the calling function. This is called as 1-way communication
/* function with args and with no return values */
#include<stdio.h>
void main()
{
          int a1=5,a2=5,a3=5;
          void sum(int,int,int);
          clrscr();
          sum(a1,a2,a3);       /* calling function with args and these args are
actual arguments will be copied into formal arguments */
}
void sum(int f1,int f2,int f3)       /* formal arguments */
{
          int s;       /*function with no return values */
          s=f1+f2+f3;
          printf("Sum of 3 nos is..%d",s);
}
Output
Sum of 3 nos is..15

With arguments and with return value.
These type of functions send values from calling function to the called function and called function will return the value to the calling function. This is called as 2-way communication
/* function with args and with return values */
#include<stdio.h>
void main()
{
          int a1=5,a2=5,a3=5,result;
          int sum(int,int,int);
          clrscr();
          result=sum(a1,a2,a3);      /* calling function with args */
          printf("sum is ...%d",result);
}
int sum(int f1,int f2,int f3)
{
          /*function with return values */
          return(f1+f2+f3);
}
Output
sum is ...15

Parameters Passing Mechanisms
The parameters can generally passed to a function in following 2 ways
  1. call by value
  2. call by reference
Call by value:
The value of each arguments are copied into the corresponding formal arguments. Any changes done to the formal parameters have no effect on actual parameters, because the actual parameters and formal parameters have separate memory locations. Calling a function by passing the value is called as “call by value”.
//call by value mechanism
#include<stdio.h>
void main()
{
          int a=10,b=50;
          void swap(int,int);
          clrscr();
          printf("Before Swapping: %d  %d\n",a,b);
          swap(a,b);
          printf("After Swapping: %d  %d\n",a,b);
}
void swap(int a,int b)
{
          int t;
          t=a;
          a=b;
          b=t;
}
Output
Before Swapping: 10  50
After Swapping: 10  50

Call by Reference
The address of actual parameters is passed with calling function. The formal parameters are pointer variables and they point to the same memory locations where the actual parameters are pointing to. Hence any changes that are done to the formal parameters effects the values of actual parameters. Calling a function by passing the address of an actual argument is called as call by reference/address.
//call by reference mechanism
#include<stdio.h>
void main()
{
          int a=10,b=50;
          void swap(int *,int *);
          clrscr();
          printf("Before Swapping: %d  %d\n",a,b);
          swap(&a,&b);
          printf("After Swapping: %d  %d\n",a,b);
}
void swap(int *a,int *b)
{
          int t;
          t=*a;
          *a=*b;
          *b=t;
}
Output
Before Swapping: 10  50
After Swapping: 50  10

Passing arrays to functions
Like the variables, it is also possible to pass the values of an array to a function, we can also even pass strings. To pass an array to a called function, it is sufficient to list the name of the array and the size of the array as arguments. For example:
          Largest(a,n);
It will pass all the elements contained in the array a of size n.

//biggest of 2 numbers
#include<stdio.h>
#include<conio.h>
void main()
{
          int b,a[10],n,i,j;
          printf("Enter the size of array:");
          scanf("%d",&n);
          printf("\nEnter the elements into array:");
          for(i=0;i<n;i++)
          scanf("%d",&a[i]);
          b=big(a,n);   //passing array to a function
          printf("\nBiggest Number is .. %d",b);
          getch();
}
int big(int a[],int n)
{
          int bi,i;
          bi=a[0];
          for(i=1;i<n;i++)
          {
                   if(a[i]>bi)
                             bi=a[i];
          }
          return (bi);
}
Output:
Enter the size of array:5
Enter the elements into array:1 2 3 4 5
Biggest Number is .. 5

bi




1
2
3
4
5
0
1
2
3
4
bi=1
i=1 => 1<5
a[1]=2
a[1]>bi so now assign bi=2


bi



1
2
3
4
5
0
1
2
3
4
bi=2
i=2 => 2<5
a[2]=3
a[2]>bi so now assign bi=3



bi


1
2
3
4
5
0
1
2
3
4
bi=3
i=3 => 3<5
a[3]=4
a[3]>bi so now assign bi=4




bi

1
2
3
4
5
0
1
2
3
4
bi=4                                                
i=4 => 4<5
a[4]=5
a[4]>bi so now assign bi=5




bi
1
2
3
4
5
0
1
2
3
4

bi=5
i=5 => 5<5    condition fail so return bi i.e., 5

Recursion
Function calling itself is called as recursion.

/* Factorial of a Number Using Recursion */
#include<stdio.h>
#include<conio.h>
int fact(int n)                                               5*fact(4);      5*24=120
{                                                                  4*fact(3);      4*6=24
    int f;                                                        3*fact(2);      3*2=6
    if(n==0)                                                    2*fact(1);      2*1=2
return 1;                                            1*fact(0);      return 1
    else                                               
       f= n * fact(n-1);         //recursion                    
       return f;
}                                                                 
void main()
{                                                                 
   int n,f;                                                     
   clrscr();                                                    
   printf("\n Enter the value of n:");
   scanf("%d",&n);
   f = fact(n);
   printf("\n The factorial of %d is %d",n,f);
}
Output:
Enter the value of n: 6
The factorial of 6 is 720

//multiplication by using recursion
#include<stdio.h>
void main()
{
          int c,a=3,b=4;                                     //a=3,b=4
          int prod(int,int);                                 4+prod(2,4);           4+8=12
          clrscr();                                              now a=2, b=4
          c=prod(a,b);                                        4+prod(1,4)            4+4=8
          printf("Product of 2 nos is: %d",c);       now a=1,b=4 return(4)
}                                                                           
int prod(int a,int b)
{
          if(a==1)
                   return b;
          else
                   return(b+prod(a-1,b));  //recursion
}
Output
Product of 2 nos is: 12