Why Have Pointers?: Numptr
Why Have Pointers?: Numptr
Why Have Pointers?: Numptr
1. The program execution time will be faster as the data is manipulated with the help of address directly.
2. Will save the memory space.
3. The memory access will be very efficient.
4. Dynamic memory is allocated.
Declaring Pointers
A pointer represents both the address and the type of an object or function. If an object or function has the
type T, then a pointer to it has the derived type pointer to T. For example, if var is a float variable, then the
expression &var whose value is the address of the float variable has the type pointer to float.
In declarations, the asterisk (*) means "pointer to." The identifier name is declared as an object with the type
type *, or pointer to type. The optional type qualifier list may contain any combination of the type qualifiers
const, volatile, and restrict.
The unary operator & gives the address of an object, so the statement
p = &c;
assigns the address of c to the variable p, and p is said to ``point to'' c. The & operator only applies to objects in
memory: variables and array elements. It cannot be applied to expressions, constants, or register variables.
Pointer Dereference
The "dereference" operation follows a pointer's reference to get the value of its pointee. The value of the
dereference of numPtrabove is 42. When the dereference operation is used correctly, it's simple. It just
accesses the value of the pointee. The only restriction is that the pointer must have a pointee for the
dereference to access. Almost all bugs in pointer code involve violating that one restriction. A pointer must be
assigned a pointee before dereference operations will work.
The unary operator * is the indirection or dereferencing operator; when applied to a pointer, it accesses the object
the pointer points to. Suppose that x and y are integers and ip is a pointer to int. This artificial sequence shows how
to declare a pointer and how to use & and *:
main()
{
int qty=5;
int *ptr;
clrscr();
ptr=&qty;
printf("Address of qty=%u\n",&qty);
printf("Address of qty=%u\n",ptr);
printf("Address of pty=%u\n",&ptr);
printf(" Vaue of ptr=%u\n",ptr);
printf(" Vaue of qty=%u\n",qty);
printf(" Vaue of qty=%u\n",*ptr);
getch();
Initialization
Bad Pointers
When a pointer is first allocated, it does not have a pointee. The pointer is "uninitialized" or simply "bad". A
dereference operation on a bad pointer is a serious runtime error. Each pointer must be assigned a pointee
before it can support dereference operations. Before that, the pointer is bad and must not be used. Bad pointers
are very common. In fact, every pointer starts out with a bad value.Correct code overwrites the bad value
with a correct reference to a pointee, and thereafter the pointer works fine.
main()
{
int *ptr;
clrscr();
*ptr=10;
printf("\nvalue of ptr=%d",*ptr);
printf("\nvalue of ptr=%d",ptr);
getch();
}
this gives an error, the pointer is uninitialized and points to a random location in memory
main()
{
int v=5;
int *ptr;
clrscr();
ptr=&v;
printf("*ptr=%d, v=%d",*ptr,v);
*ptr=10;
printf("\n*ptr=%d, v=%d",*ptr,v);
getch();
}
Null Pointer
The constant NULL is a special pointer value which encodes the idea of "points to nothing." It turns out to be
convenient to have a well defined pointer value which represents the idea that a pointer does not have a
pointee. It is a runtime error to dereference a NULL pointer. We can teset the condition for a null pointer using
if (ptr==NULL) or even set a pointer to NULL to indicate that its no longer in use.
main()
{
int *ptr=NULL;
clrscr();
printf("\nvalue of ptr=%d",ptr);
getch();
Pointer to Pointer
Pointer variable can be assigned the address of an ordinary variable. Now this variable itself could be another
pointer. This means that a pointer can contain address of another pointer.
main()
{
int i=100;
int *pi;
int **pii;
clrscr();
pi=&i;
pii=π
printf("Address of i=%u\n",&i);
printf("Address of i=%u\n",pi);
printf("Address of pi=%u\n",*pii);
printf("Address of pi=%u\n",&pi);
printf("Address of pi=%u\n",pii);
printf("Address of pii=%u\n",&pii);
printf("Value of i=%d\n",i);
printf("Value of i=%d\n",*(&i));
printf("Value of i=%d\n",*pi);
printf("Value of i=%d\n",**pii);
getch();
}
Pointers to pointers are not restricted to the two-stage indirection illustrated here. You can define pointers with
as many levels of indirection as you need. However, you cannot assign a pointer to a pointer its value by mere
repetitive application of the address operator:
Pointer Arithmetic
Besides using assignments to make a pointer refer to a given object or function, you can also modify an object
pointer using arithmetic operations. When you perform pointer arithmetic, the compiler automatically adapts
the operation to the size of the objects referred to by the pointer type.
Ptr1=ptr2+3
Ptr++
--ptr;
ptr++ will cause the pointer ptr to point the next address value of its type.
main() *ptr1=*ptr2+5;
{ prod=*ptr1**ptr2;
int res=100; quo=*ptr1/ *ptr2;
int a=5,prod,quo;
int *ptr1; printf("Value of res=%d\n",res); 105
int *ptr2; printf("Value of a=%d\n",a);110
clrscr(); printf("Value of prod=%d\n",prod);11550
ptr1=&a; printf("Value of quo=%d\n",quo);1
ptr2=&res; getch();
res=res+*ptr1; }
#include<stdio.h> clrscr();
#include<conio.h>
void swapval(int,int); printf("Pass by Value\n");
void swapref(int*,int*); printf("\nBefore calling function x=%d,y=%d",x,y);
void main() swapval(x,y);
{ printf("\nAfter calling function x=%d,y=%d",x,y);
int x=10,y=20; printf("\nPass by Reference\n");
printf("\nBefore calling function x=%d,y=%d",x,y); return;
swapref(&x,&y); }
printf("\nAfter calling function x=%d,y=%d",x,y);
getch(); void swapval(int x,int y)
} {
void swapref(int *x,int *y) int t;
{ t=x;
int t; x=y;
t=*x; y=t;
*x=*y; printf("\nWithin swapval x=%d and y=%d\n",x,y);
*y=t; return;
printf("\nWithin swapref x=%d and y=%d\n",*x,*y); }
main()
{
float len,br;
float peri,ar;
void periarea(float lenght,float breadth,float *,float*);
printf("\nEnter the length and breadth of rectangle in meters:\n");
scanf("%f%f",&len,&br);
periarea(len,br,&peri,&ar);
printf("\nPerimeter of the rectangel is %.2f meters",peri);
printf("\nArea of the rectangle is %.2f sq meters",ar);
getch();
}
void periarea(float length,float breadth,float *perimeter,float*area)
{
*perimeter=2*(length+breadth);
*area=length*breadth;
}
int *func();
main()
{
int *a;
clrscr();
a=func();
printf("address=%u\n",a);
printf("Value=%d",*a);
getch();
}
int *func()
{
int r=5;
printf("\nR address=%d\n",&r);
return(&r);
}
Pointer and array
Pointers occur in many C programs as references to arrays , and also as elements of arrays. A pointer to an
array type is called an array pointer for short, and an array whose elements are pointers is called a pointer
array.
If arr is a one dimensional array the address of the first array element can be written as &arr[0] or simply arr.
Moreover the address of the second array element can be written as %arr[1] or simply (arr+1).
main()
{
static int x[10]={10,11,12,54,23,56,21,14,56,51};
int i;
clrscr();
for(i=0;i<=9;++i)
{
printf("\n i=%d x[i]=%d *(x+i)=%d ",i,x[i],*(x+i));
printf("&x[i]=%x x+i=%x",&x[i],(x+i));
}
getch();
}
Conventional array definition results in a fixed block of memory being reserved at the beginning of program
execution whereas this does not occur if the array is represented in terms of a pointer variable. Therefore the use of
a pointer variable to represent an array requires some type of initial memory assignment before the array elements
are processed. This is known as dynamic memory allocation
When writing a program, it is often known that how much data it will have to process; or you can anticipate
that the amount of data to process will vary widely. In these cases, efficient resource use demands that you
allocate memory only as you actually need it at runtime, and release it again as soon as possible. This is the
principle of dynamic memory management, which also has the advantage that a program doesn't need to be
rewritten in order to process larger amounts of data on a system with more available memory.
The two functions for allocating memory, malloc( ) and calloc( ), have slightly different parameters:
int day_of_year(int year, int month, int day); int day_of_year(int year, int month, int day)
char *month_name(int n); {
main() int i, leap;
{ leap = year%4 == 0 && year%100 != 0 || year
int year,month,day,tot; %400 == 0;
clrscr(); for (i = 1; i < month; i++)
printf("enter year, month , day="); day += daytab[leap][i];
scanf("%d %d %d",&year,&month,&day); return day;
tot=day_of_year(year,month,day); }
printf("total days=%d",tot); /* month_name: return name of n-th month */
printf("\nmonth name= char *month_name(int n)
%s",month_name(month)); {
getch(); static char *name[] = {
} "Illegal month",
"January", "February", "March",
static char daytab[2][13] = { "April", "May", "June",
{0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}, "July", "August", "September",
{0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31} "October", "November", "December"
}; };
return (n < 1 || n > 12) ? name[0] : name[n];
/* day_of_year: set day of year from month & }
day */
/*subtract matrices*/
#include<stdio.h> int
#include<conio.h> *a[MAXROWS],*b[MAXROWS],*c[MAXROWS];
#include<stdlib.h> printf("How many rows=");
#define MAXROWS 20 scanf("%d",&nrows);
#define MAXCOLS 30 printf("How many cols=");
void readinput(int *a[MAXROWS],int nrows,int scanf("%d",&ncols);
ncols); for(row=0;row<=nrows;row++)
void compute(int *a[MAXROWS],int {
*b[MAXROWS],int *c[MAXROWS],int nrows,int a[row]=(int*)malloc(ncols*sizeof(int));
ncols); b[row]=(int*)malloc(ncols*sizeof(int));
void write(int *c[MAXROWS],int nrows,int ncols); c[row]=(int*)malloc(ncols*sizeof(int));
main() }
{ printf("\nFIRST TABLE\n\n");
int row,nrows,ncols; readinput(a,nrows,ncols);
printf("\nSECOND TABLE\n\n");
readinput(b,nrows,ncols); int row,col;
compute(a,b,c,nrows,ncols); for(row=0;row<m;++row)
printf("\nSUM OF TWO TABLE\n\n"); {
write(c,nrows,ncols); for(col=0;col<n;++col)
getch(); *(c[row]+col)=*(a[row]+col)-*(b[row]+col);
} }
void readinput(int *a[MAXROWS],int m,int n) return;
{ }
int row,col; void write(int *c[MAXROWS],int m,int n)
for(row=0;row<m;++row) {
{ int row,col;
printf("\nEnter date for row no .%2d\n",row+1); for(row=0;row<m;++row)
for(col=0;col<n;++col) {
scanf("%d",&a[row][col]); for(col=0;col<n;++col)
} printf("%4d",*(c[row]+col));
return; printf("\n");
} }
void compute(int *a[MAXROWS],int return;
*b[MAXROWS],int *c[MAXROWS],int m,int n) }
{