Documenti di Didattica
Documenti di Professioni
Documenti di Cultura
There are many reasons for using pointers. A pointer allows a function or a program to access a variable outside the preview of function or program. Use of pointer increases makes the program execution faster. Using pointers, arrays and structures can be handled in more efficient way. To communicate with operating system about memory.
UNDERSTANDING POINTERS
Each memory location is assigned a unique number called location number or address.
A memory cell is either of one byte or more contagious bytes. Each cell can store one value at a given time. The address of a cell is always the address of first byte.
Since pointer is a variable, its value is also stored in memory in another address. Suppose we assign the address of variable var to a variable ptr.
The actual address of a variable is system dependent. During compilation and linking, addresses are assumed to be relative to some base address, usually 0. When the operating system loads the program in a free block, all the address are transformed with relative to address of the first memory location of the free block. Consider the following statement :
ptr = &code;
Where type is a pre-defined or user-defined data types and indicates that the pointer will point to the variables of that specific data type, and character * indicates that variable is a pointer variable. For example the statement
int *ptr1;
Declares a pointer varieble ptr1 that can point to an integer type variable.
Once a pointer has been assigned the address of variable, the question remains as how to access the value of the variable using the pointer. This is done using indirection operator(*). Consider the following statements
: int *ptrX, x = 10, y; ptrX = &x; y = *ptr X; cout << \nValue of variable x = << x; cout << \nValue of variable pointed to by ptrX = << *ptrX; cout << \nAddress of variable x = << ptrX; cout << \nValue of variable y = << y << \n; :
// //
#include <iostream.h> void main() { int *ptrX, x = 10, y; ptrX = &x; y = &ptrX; cout << \nValue of variable x = << x; cout << \nValue of variable pointed to by ptrX = << *ptrX; cout << \nAddress of variable x = << ptrX; cout << \nValue of variable y = << y << \n; }
A pointer is a variable that holds the address of another variable. We can have a variable that in turn holds an address of another variable. This type of variable will be known as pointer to pointer. A pointer to a pointer will be declared as:
int **ptr;
// Program to illustrate the use of double indirection #include <iostream.h> void main() { int a = 5, *ptrA, **ptrPtrA; ptrA = &a; cout << \nAddress of a = << &a; cout << \nValue of a = << a; cout << \nAddress of ptrA = << &ptrA; cout << \nValue of ptrA = << ptrA; cout << \nValue pointed to by ptrA = << *ptrA; cout << \nAddress of ptrPtrA = << &ptrPtrA; cout << \nValue of ptrPtrA = << ptrPtrA; cout << \nValue pointed to by ptrPtrA = << **ptrPtrA; cout << \n; }
C++ language provides a set of operators called dynamic memory management operators to allocate and de-allocate memory at execution time, i.e. dynamically. new operator delete operator
The new operator allocates the memory and always returns a pointer to an appropriate type. The new operator is defined as:
type * new type [ size in integer ] ;
The following illustrates its use:
int *intPtr; intPtr = new int [100];
Allocates memory block of 200 bytes, 2 bytes for one integer value, total of 100 integers. The new operator also permits the initialisation of memory locations during allocation. The syntax for doing so is:
type *ptrVar = new type ( InitialValue);
The delete operator is a counterpart of new operator and it deallocates memory allocated by the new operator back to the free poll of memory. The syntax of delete operator is defined as:
delete ptrVar;
Where ptrVar can be a simple pointer variable or the name of the array of pointer to all types excepts class type. However, if ptrVar is an array of pointers to objects then we have to use the delete operator as shown below:
delete ptrVar[]; or delete [] ptrVar;
The second form is very handy if we want to deallocate more that one array with single use of delete operator.
We can use pointers for structure variables. Consider the following declarations:
struct EMPLOYEE { int code; char name[20]; int deptCode; float salary; }; EMPLOYEE emp, *empPtr;
These declarations create user-defined data type and give it name EMPLOYEE. It also declares emp as variable of type employee and empPtr as pointer variable to type employee. Now the following statement
ptr = &emp1;
Can be used to assign the address of variable emp1 to pointer variable ptr.
You may expect that the elements can be accessed as shown below:
*ptr.code *ptr.name *ptr.dept_code *ptr.salary
But this approach will not work as the dot operator . has higher priority than the indirection operator *. The correct way is to write as:
(*ptr).code (*ptr).name (*ptr).dept_code (*ptr).salary
The syntax for accessing members of structures using arrow operator is:
ptr->vname
#include <iostream.h> using namespace std; class cl { int i; public: cl(int j) { i=j; } int get_i() { return i; } }; int main() { cl ob(88), *p; p = &ob; // get address of ob cout << p->get_i(); // use -> to call get_i() return 0; }
POINTER TO AN OBJECT
When a pointer is initialized with the address of an object, then its members can be accessed using arrow -> operator.
#include <iostream.h> using namespace std; class cl { public: int i; cl(int j) { i=j; } }; int main() { cl ob(1); int *p; p = &ob.i; // get address of ob.i cout << *p; // access ob.i via p return 0; }
POINTER TO A MEMBER
To obtain address of a member, the address of & operator is used along with fully qualified member name. A class member pointer is declared using the operator ::* , acombinatio of two characters without any space. Consider the following class:
class Sample { private: int m; // . . . public: void show() // . . . };
#include <iostream.h> using namespace std; class cl { public: cl(int i) { val=i; } int val; int double_val() { return val+val; } }; int main() { int cl::*data; // data member pointer int (cl::*func)(); // function member pointer cl ob1(1), ob2(2); // create objects data = &cl::val; // get offset of val func = &cl::double_val; // get offset of double_val() cout << "Here are values: "; cout << ob1.*data << " " << ob2.*data << "\n"; cout << "Here they are doubled: "; cout << (ob1.*func)() << " "; cout << (ob2.*func)() << "\n"; return 0; }
All non-static member functions of an object have access to a special pointer named this. The this pointer holds the address of the object whose member function is invoked.
//Program to demonstrate that this pointer is passed as //implicit first argument to a member function #include<iostream.h> #include<iomanip.h> class Sample { private: int a; int b; public: void showAddress () { cout<< endl << My objects address is <<this << endl; } }; void main() { Sample s1,s2,s3 //create objects s1.showAddress(); // call member function s2.showAddress(); s3.showAddress(); }
Like structures, there are the classes where atleast one of the data members is a pointer to itself. These types of classes are useful for building complex data structures.
class List { private : int data; List *next; public: // . . . Member functions };