Subscribe to our RSS Feeds
Hello, this is a sample text to show how you can display a short information about you and or your blog. You can use this space to display text or image introduction or to display 468 x 60 ads and to maximize your earnings.

Pointers

0 Comments »

Pointers
A pointer is a variable that holds address (memory location) of another variable rather than actual value. Also, a pointer is a variable that points to or references a memory location in which data is stored. Each memory cell in the computer has an address that can be used to access that location.  So, a pointer variable points to a memory location and we can access and change the contents of this memory location via the pointer. Pointers are used frequently in C, as they have a number of useful applications. In particular, pointers provide a way to return multiple data items from a function via function arguments.
Pointer Declaration
Pointer variables, like all other variables, must be declared before they may be used in a C program. We use asterisk (*) to do so. Its general form is:
data-type *ptrvar;
For example,
int* ptr;
This statement declares the variable ptr as a pointer to int, that is, ptr can hold address of an integer variable.
Once we declare a pointer variable we can point by it to something. We can do this by assigning to the pointer the address of the variable you want to point as in the following example:
int var=11,*ptr;
ptr=&var;
This places the address where var is stores into the variable ptr. For example, if var is stored in memory 21260 address then the variable ptr has the value 21260.
We can access the contents of the variable pointed by pointer using an asterisk (*) in front of a variable name. For example,
int var=11,*ptr;
ptr=&var;
*ptr=45; //It changes the value of var to 45
Example:
#include<stdio.h>
#include<conio.h>
void main() {
            int var=11,*ptr;
            clrscr();
printf("%d\n",var); //prints 11
            printf("%d\n",&var); //prints address of var
printf("%d\n",*&var); //prints 11
            ptr=&var;
            printf("%d\n",ptr); //prints address of var
            printf("%d\n",*ptr); //prints 11
            *ptr=45;
            printf("%d\n",var); //prints 45
            printf("%d\n",*ptr); //prints 45
            getch();
}
The operator ‘&’ is called “address of” operator. The expression &var returns the address of the variable var. The operator ‘*’ called “value at address” operator. It gives the value stored at a particular address. The “value at address” operator is also called “indirection operator”.
Passing (call) by Value and Passing (call) by Reference
Arguments can generally be passed to functions in one of the two ways:
  • Sending the values of the arguments (pass by value)
  • Sending the addresses of the arguments (pass by reference)
Pass by value: In this method, the value of each of the actual arguments in the calling function is copied into corresponding formal arguments of the called function. With this method the changes made to the formal arguments in the called function have no effect on the values of actual arguments in the calling function. The following program illustrates ‘call by value’.
#include<stdio.h>
#include<conio.h>
void main()
{
            int a,b;
            void swap(int, int );
            clrscr();
            a = 10;
            b = 20;
            swap(a,b);
            printf("a = %d\tb = %d",a,b);
            getch();
}
void swap(int x, int y)
{
            int t;
            t = x;
            x = y;
            y = t;
            printf("x = %d\ty = %d\n",x,y);
}
The output of the above program would be
x = 20 y = 10
a = 10 b = 20
Note that values of a and b remain unchanged even after exchanging the values of x and y.
Pass by reference: In this method, the addresses of actual arguments in the calling function are copied into formal arguments of the called function. This means that using these addresses we would have an access to the actual arguments and hence we would be able to manipulate them. The following program illustrates this fact.

#include<stdio.h>
#include<conio.h>
void main()
{
            int a,b;
            void swap(int*, int*);
            clrscr();
            a = 10;
            b = 20;
            swap(&a,&b);
            printf("a = %d\tb = %d",a,b);
            getch();
}
void swap(int *x, int *y)
{
            int t;
            t = *x;
            *x = *y;
            *y = t;
            printf("x = %d\ty = %d\n",*x,*y);
}
The output of the above program would be
x = 20 y = 10
a = 20 b = 10
Note: We can use call by reference to return multiple values from the function.
Pointers and Arrays
An array name by itself is an address, or pointer. A pointer variable can take different addresses as values. In contrast, an array name is an address, or pointer, that is fixed.
Pointers and One-dimensional Arrays
In case of one dimensional array, an array name is really a pointer to the first element in the array. Therefore, if x is a one-dimensional array, then the address of the first array element can be expressed as either &x[0] or simply x. Moreover, the address of the second array element can be expressed as either &x[1] or as (x+1), and so on. In general, the address of array element (x+i) can be expressed as either &x[i] or as (x+i). Thus we have two different ways to write the address of any array element: we can write the actual array element, preceded by an ampersand; or we can write an expression in which the subscript is added to the array name.
Since, &x[i] and (x+i) both represent the address of the ith element of x, it would seem reasonable that x[i] and *(x+i) both represent the contents of that address, i.e., the value of the ith element of x. The two terms are interchangeable. Hence, either term can be used in any particular situation. The choice depends upon your individual preferences. For example,
/* Program to read n numbers in an array and display their sum and average */
#include<stdio.h>
#include<conio.h>
#define SIZE 100
void main()
{
            float a[SIZE],sum=0,avg;
            int n,i;
            clrscr();
            printf("How many numbers?");
            scanf("%d",&n);
            printf("Enter numbers:\n");
            for(i=0;i<n;i++)
            {
                        scanf("%f",(a+i)); // scanf("%f",&a[i]);
                        sum=sum+*(a+i); //sum=sum+a[i];
            }
            avg=sum/n;
            printf("Sum=%f\n",sum);
            printf("Average=%f",avg);
            getch();
}
Pointers and Multidimensional Arrays
Since one-dimensional array can be represented in terms of a pointer, a multidimensional array can also be represented with an equivalent pointer notation. A two-dimensional array, for example, is actually a collection of one-dimensional arrays. Therefore, we can define a two-dimensional array as a pointer to a group of contiguous one-dimensional arrays.
Suppose x is a two-dimensional integer array having 10 rows and 20 columns. We can declare x as
int (*x)[20];
rather than
int x[10][20];
In the first declaration, x is defined to be a pointer to a group of contiguous, one-dimensional, 20-element integer arrays. Thus, x points to the first 20-element array, which is actually the first row (i.e., row 0) of the original two-dimensional array. Similarly, (x+1) points to the second 20 element array, which is the second row (row 1) of the original two-dimensional array, and so on. Now, we can access the element in row 2 (third row) and column 5 (sixth column) by writing either x[2][5] or *(*(x+2)+5). In general, we can access the element in row i and column j by writing x[i][j] or *(*(x+i)+j). For example,
#include<stdio.h>
#include<conio.h>
#define ROW 3
#define COL 2
void main()
{
int a[ROW][COL],b[ROW][COL],i,j,sum;
            clrscr();
            printf("Enter elements of first matrix:\n");
            for(i=0;i<ROW;i++)
            {
                        for(j=0;j<COL;j++)
                                    scanf("%d",(*(a+i)+j));
                        printf("\n");
            }
            printf("Enter elements of second matrix:\n");
            for(i=0;i<ROW;i++)
            {
                        for(j=0;j<COL;j++)
                                    scanf("%d",(*(b+i)+j));
                        printf("\n");
            }
            printf("Addition matrix is:\n");
            for(i=0;i<ROW;i++)
            {
                        for(j=0;j<COL;j++)
                        {
                                                sum=*(*(a+i)+j)+*(*(b+i)+j);
                                    printf("%d\t",sum);
                        }
                        printf("\n");
            }
            getch();
}
Dynamic Memory Allocation
Dynamic memory allocation is the process of allocating memory in a program dynamically at run time. C provides two basic functions calloc() and malloc() for this purpose. The name calloc stands for “contiguous allocation” and the name malloc stands for “memory allocation”.
The programmer uses calloc() and malloc() to dynamically create space arrays, structures, and unions.
The function calloc() takes two arguments both of unsigned integral type. When we call this function, it allocates contiguous space in memory. For example,
/* Program to read n floating point numbers and display their sum and average using pointer and dynamic memory allocation*/
#include<stdio.h>
#include<conio.h>
#include<stdlib.h>
void main()
{
            float *a,sum=0,avg;
            int n,i;
            clrscr();
            printf("How many numbers?");
            scanf("%d",&n);
            a=(float*)calloc(n,sizeof(float));
            printf("Enter numbers:\n");
            for(i=0;i<n;i++)
            {
                        scanf("%f",(a+i)); //scanf("%f",&a[i]);
                        sum=sum+*(a+i); //sum=sum+a[i];
            }
            avg=sum/n;
            printf("Sum=%f\n",sum);
            printf("Average=%f",avg);
            free(a);
            getch();
}
In the above program a points to the first memory block in the allocated memory.
The programmer uses malloc() in a similar fashion. This function takes a single argument of unsigned integral type. For example,
a=(float*)mallocc(n*sizeof(float));
When we use calloc(), the space is initialized with all bits set to zero. Unlike, calloc(), the function malloc() does not initialize the space in memory that it makes available. In a large program, malloc() may take less time.
Space that has been dynamically allocated with either calloc() or malloc() does not destroyed automatically. The programmer must use free() explicitely to destroy it. For example,
free(a);
Operations on Pointers (Pointer Arithmetic)
Not all operations are applied for pointers. Permissible operations that can be applied for pointers are given below:
  1. A pointer variable can be assigned the address of an ordinary variable. For example, pv = &v, where pv is a pointer variable and v is an ordinary variable.
  2. A pointer variable can be assigned the value of another pointer variable provided both pointers point to objects of the same data type. For example, pv = px, where both pv and px are pointer variables of the same data type.
  3. A pointer variable can be assigned a null (zero) value. For example, pv = NULL, where NULL is a symbolic constant that represent the value zero and pv is a pointer variable.
  4. An integer quantity can be added to or subtracted from a pointer variable. For example, pv+3, ++pv etc. where pv is a pointer variable.
  5. One pointer variable can be subtracted from another provided both pointers point to elements of the same array.
  6. Tow pointer variables can be compared provided both pointers point to objects of the same data type.
Other arithmetic operations on pointers are not allowed. Thus, a pointer variable cannot be multiplied by constant; two pointer variables cannot be added; and so on.
Pointer Constant and Pointer to Constant
Pointer constant or constant pointer means the pointer is constant. For example, int *const ptr2 indicates that ptr2 is a pointer which is constant. This means that ptr2 cannot be made to point to another integer after it points to some integer. However the integer pointed by ptr2 can be changed. For example,
int a=2,b=3;
int *const ptr2 = &a;
ptr2=&b; //error
It is not a pointer to constant. A pointer to constant is written like
const int *ptr1. It indicates that ptr1 is a pointer that points to a constant integer. The integer is constant and cannot be changed. However, the pointer ptr1 can be made to point to some other integer constant. For example,
const int a=2;
const int *ptr2 = &a;
*ptr2=8; //error
3:45 PM

0 Responses to "Pointers"

Post a Comment