ProgrammingProgramming inin C++C++ 7.7. PointersPointers && arraysarrays

! Introduction ! ‘address-of’ operator ! Dereferencing or indirection operator ! Idea of pointer ! Declaring pointers ! Using pointers ! Pointers to pointers ! Pointers and memory ! NULL pointer ! Summary 1 Introduction to programming in C++ for engineers: 7. Pointers & arrays IntroductionIntroduction It is hardly possible to perform in efficient scientific calculations without arrays which are in C++ closely related to so called pointers. The memory of the computer can be regarded as the collection of labelled storage locations. Let us assume that we can access memory in any order. A very simplified picture is to visualize memory as a linear sequence of storage locations, one byte in size, which are labelled by numbers. A particular label is known as the address of the corresponding memory element. The two operations of interest are: - to read what is stored at particular address, - to write to the memory labelled by an address.

2 Introduction to programming in C++ for engineers: 7. Pointers & arrays ‘address‘address--of’of’ operatoroperator In C++ the address of any variable can always be found by preceding the variable with the address-of operator denoted by &. The address-of operator has the same precedence and right to left associativity as other unary operators. The & operator means: return the address of the variable to the right. There are a few things that we cannot do with the address-of operator. It is illegal to take the address of the constant. &3.141529; //WRONG: cannot take the address of constant It is also illegal to take the address of an expression. &(k + 2); //WRONG: cannot take the address of expression

3 Introduction to programming in C++ for engineers: 7. Pointers & arrays DereferencingDereferencing oror indirectionindirection operatoroperator Given an address there is an operator known as dereference operator denoted by * which returns the value stored at that particular address. This operator is also called indirection operator. In some sense address-of and indirection operators are inverse of each other: -If k is a variable of type int - then &k is the address of memory where that variable is stored. - The value stored at the memory location &k is given by *&k. int k, l; l=*&k; //isn’tsimplertowritel=k The address-of and indirection operators are only inversed in a limited sense. &*k would be meaningless in this context since k is not an address and so cannot be dereferenced. The indirection operator should not be confused with the multiplication operator, which is binary.

4 Introduction to programming in C++ for engineers: 7. Pointers & arrays IdeaIdea ofof pointerpointer The value of a particular variable is held at a location in memory with some specific address. The most significant is starting address, the actual number of bytes used varies with the variable type and C++ compiler. It is useful to have variables which can hold the address of a storage location. We can efficiently sort the data by manipulating addresses rather than copying the data itself. Variables for storing memory addresses are called pointers. There is a special pointer type corresponding to each variable type. The different pointer types are needed because it is usually necessary to know how much memory is being pointed to (the size of the type) and how the bits stored in memory should be interpreted.

5 Introduction to programming in C++ for engineers: 7. Pointers & arrays DeclaringDeclaring pointerspointers int *p1 // p1 is a pointer to the type int The notation for pointer declarations may seem peculiar but it can be understood by recalling that * is the dereferencing operator. This operator returns the value stored at the address held by its (right) operand. White space is ignored so some unusual variations are possible: int*p1; int * p1; int* p1; In order to define a number of pointers we may be tempted to use: int *p1, p2, p3; // WRONG!!! p2, p3 are not pointers The indirection operator like all unary operators binds to the right, not the left. To correctly implement our idea we need: int *p1, *p2, *p3; It is better not to use a single statement to simultaneously declare both identifiers of a type and pointers to that type.

6 Introduction to programming in C++ for engineers: 7. Pointers & arrays UsingUsing pointerspointers Dereferenced pointers can be used anywhere that an identifier of the corresponding type would be valid: int i, j, k; // integer variables int *pt_i, *pt_j; // pointers to integers

pt_i = &i; // assigning the address of i pt_j = &j; // assigning the address of j i=2; j=3; k = *pt_i + *pt_j; // 5 is assigned to k *pt_i = 10; // 10 is assigned to i A dereferenced pointer can appear on the left of the assignment operator - the assignment can be made to the object that the pointer points to. The indirection operator has the highest precedence of any operator introduced sofar, apart from the function call operator.

7 Introduction to programming in C++ for engineers: 7. Pointers & arrays UsingUsing pointerspointers A pointer can point to a const type, but the pointer definition must also include the const specifier: constintw=100; const int *pt_c; int *pt_i; pt_c = &w; ++pt_c; pt_i = &w; // WRONG a non-const pointer cannot // point to a const Although we cannot take the address of a constant we can take the address of a const type. It is essential to distinguish between a pointer to a const type (described above) and a const pointer. double x = 127; double *const pt = &x; ++*pt; // OK! x is not a constant ++pt; // WRONG! pt is a constant

8 Introduction to programming in C++ for engineers: 7. Pointers & arrays PointersPointers toto pointerspointers A pointer is simply a variable which is used to hold the address of another variable, so it is possible to store the address of a pointer. A variable used to store the address of a pointer is known as a pointer to a pointer. double x; // memory defined to store a double double *pt; // memory defined to store the // address of a double double **pt_pt; // memory defined to store the // address of a pointer to a double The value stored by pt can be accessed by dereferencing pt_pt whereas to access x we need to dereference pt_pt twice. The relation between the three storage locations is shown below.

*pt_pt *pt pt_pt pt x

9 Introduction to programming in C++ for engineers: 7. Pointers & arrays PointersPointers andand memorymemory Pointers are extremely powerful tool. Like most powerful tools they can be abused. int *pt_i; ... *pt_i = 10; Since we do not know where pt_i points some arbitrary area of memory gets assigned the value 10. When using pointers you must make certain you get them right. A related and quite common error is to forget to allocate any memory for the pointer to point to.

10 Introduction to programming in C++ for engineers: 7. Pointers & arrays NullNull pointerpointer There is a special constant pointer, known as a null pointer, which is guarantied not to be a valid . The constant NULL defined in is normally used as a value of the null pointer. Assigning zero to a pointer is the same as assigning NULL although strictly the zero is converted to the null pointer which may not have the same bit pattern as 0. Since the null pointer cannot be a valid address we have a very useful way of signalling certain error conditions involving memory locations.

11 Introduction to programming in C++ for engineers: 7. Pointers & arrays SummarySummary ! A pointer is a variable that can be used to store an address: double *pt; ! The address of an object can be found by using the address-of operator &. A particular address is accessed by means of the dereferencing or indirection operator *: double x; double *pt = &x; ! It is illegal to take the address of a constant: or an expression: &10; // WRONG!!! &(x+3.1415); // WRONG!!! ! Memory must be defined for a pointer to point to: double *pt; *pt = 3.1415; // WRONG!!! ! The null pointer NULL is defined in and is guarantied to be an invalid address.

12 Introduction to programming in C++ for engineers: 7. Pointers & arrays