0% found this document useful (0 votes)
0 views

Pointers in C programming - SOICT - Data structures & Algorithms - IT3010E

The document provides an overview of pointers in C++, covering topics such as obtaining variable addresses, pointer variables, pointer arithmetic, and dynamic memory allocation. It includes examples and explanations of how pointers relate to arrays and how they can be used as function parameters. Additionally, it emphasizes the importance of proper pointer initialization and dereferencing.
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
0 views

Pointers in C programming - SOICT - Data structures & Algorithms - IT3010E

The document provides an overview of pointers in C++, covering topics such as obtaining variable addresses, pointer variables, pointer arithmetic, and dynamic memory allocation. It includes examples and explanations of how pointers relate to arrays and how they can be used as function parameters. Additionally, it emphasizes the importance of proper pointer initialization and dereferencing.
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 15

Contents

Hanoi University of Science and Technology


TRƯỜNG ĐẠI HỌCSchool
BÁCH of KHOA
Information and Communications Technology
HÀ NỘI
VIỆN CÔNG NGHỆ THÔNG TIN VÀ TRUYỀN THÔNG
1. Getting the Address of a Variable
2. Pointer Variables
3. The Relationship Between Arrays and Pointers
4. Pointer Arithmetic
Chapter. Pointers 5. Initializing Pointers
6. Pointers as Function Parameters
Nguyễn Khánh Phương 7. Pointer to constants
Computer Science department 8. Dynamic Memory Allocation
School of Information and Communication Technology
E-mail: [email protected]
(read Chapter 9. Starting Out with C++: From Control Structures
through Objects, Tony Gaddis) 2

Contents 1. Getting the Address of a Variable


1. Getting the Address of a Variable • When the program
Addresses inruns, the computer allocated contiguous
Memory
2. Pointer Variables blocks of memory (called as User Space) to user.
• Memory is divided into “memory cells”.
3. The Relationship Between Arrays and Pointers • Each cell has an unique address.
4. Pointer Arithmetic • The size of each cell is 1 byte

5. Initializing Pointers Address Value stored in address

6. Pointers as Function Parameters


7. Pointer to constants
8. Dynamic Memory Allocation

(read Chapter 9. Starting Out with C++: From Control Structures


through Objects, Tony Gaddis) 3 4
1. Getting the Address of a Variable 1. Getting the Address of a Variable
• When a variable is declared, enough memory to hold a value of that • The address of a non-array variable can be obtained by using the
Addresses in Memory
type is allocated for it at an unused memory location. This is the
Obtaining Memory Addresses
address operator &
address of the variable. x
0x70fe0c 0x70fe08 0x70fe07
int x; //4 bytes
x number ch
x = 5;
• Assume variable x is stored in 4
memory cells starting at address 1000110.
• Value of variable x is 5 (4 memory
cells are used to store this value).
• To get the address of first memory cell
allocated to variable x, we use address operator &
 &x will return the value = 1000110
5 // prints address in hexadecimal 6
Address of variable x

1. Getting the Address of a Variable Contents


• Each variable in program is stored at a unique address
Obtaining Memory Addresses • Use address operator & to get address of a variable 1. Getting the Address of a Variable
2. Pointer Variables
3. The Relationship Between Arrays and Pointers
4. Pointer Arithmetic
5. Initializing Pointers
6. Pointers as Function Parameters
7. Pointer to constants
8. Dynamic Memory Allocation

7 8
2. Pointer Variables 2. Pointer Variables
• A pointer is a variable that stores the address of something else.  A pointer is a variable that holds
the address of something else. MEMORY
• Declare pointer: Address
 Pointer points to the data. 0
type *pointer_name; 1
int x = 123; 2
Use asterisk ( * ) to show this is pointer //Declare an int, assign the value of 123
x 3 123
• There are many types of variables with different sizes, so there are int *ptr;//declare a pointer to an int 4
also many types of pointers. (Example: int pointer to point to a 5
//same as int* ptr;
variable or function of type int).

...

...
//or int * ptr;
Example:
int *countPtr; //This is read as “countPtr is a pointer to an int” ptr = &x; //assign ptr the memory address of x
ptr 345 3
double *tPtr; //This is read as “tPtr is a pointer to a double”
346
• A Pointer may be initialized to 0, NULL, or an address.
Address of x is value of ptr 347
• NULL is a Symbolic constant defined in <iostream> to represent the
value 0.
• A Pointer that is assigned 0 or NULL points to nothing. 9 10

Dereference a pointer Example: Pointer


• To declare pointer: type *pointer_name; int c;
• Assign value to pointer (get address of other object and assign this address to int *ptr; /* Declare variable ptr is an int pointer*/
the pointer): pointer_name = &var_name; c = 7;
(type of pointer_name and var_name must be the same) ptr = &c;
• Access the object that the pointer points to: *pointer_name
(dereference the pointer) printf(“%d”, *ptr); /* print 7*/
Example: *ptr = 80;
double foo = 3.2; printf(“%d”, c); /* print 80 */
double *ptr; ptr =&foo; //double *ptr = &foo;
C
cout << *ptr << endl; // this prints 3.2
• A pointer must have a value before you can dereference it (follow the pointer). … 7 3 4 …
Address 172 173 174 175 176 177 178 179 180 181

int *ptr; int foo;


*ptr = 3; int *ptr = &foo;
ptr
*ptr = 3;
… 174 3 4 …
Address 832 833 834 835 836 837 838 839 840 841

11 12
Pointers to anything Contents
1. Getting the Address of a Variable
x some int 2. Pointer Variables
int *x; 3. The Relationship Between Arrays and Pointers
int **y; 4. Pointer Arithmetic
y some *int some int
5. Initializing Pointers
6. Pointers as Function Parameters
double *z;
z some double 7. Pointer to constants
8. Dynamic Memory Allocation

13 14

Pointer and 1D array Pointer in expressions


• Array name can be used as a pointer constant: • Integer math operations can be used with pointers.
int a[] = {4, 7, 11, 5, 23}; • If you increase a pointer, it will be increased by the size of whatever it
points to.
cout << a; //display address of a[0] ptr ~ address of a[0]
//same as: cout << &a[0]; int a[5]; ptr+i ~ address of a[i]
cout << *a; //displays 4 (value of a[0]) int *ptr = a; Value of a[i]~ a[i]
~ ???? *(ptr+i)

• Pointer can be used as an array name: *ptr *(ptr+2) *(ptr+4) ptr[i] ~ value of a[i]

int *ptr = a; //ptr store address of a[0] &ptr[i] ~ address of a[i]

cout << ptr[1]; //displays 7 (value of a[1]) a[0] a[1] a[2] a[3] a[4]

int a[5]; Value of a[i]: a[i] or ptr[i] or *(ptr+i)


ptr[i] ~ value of a[i]
int *ptr = a; Address of a[i]: &a[i] or &ptr[i] or (ptr+i)
&ptr[i] ~ address of a[i]
15 16
Example Example: Write C++ program to print address of each element in a 1D-array

#include <iostream>
Write C++ program to print address of each element in a 1D-array:
using namespace std;
#include <iostream>
int main()
using namespace std;
int main() Result in DevC { int A[ ] = {5, 10, 12, 15, 4};

{ (sizeof(int)=4) cout<<"Address Contents\n";


&A[i] : address of element A[i]
for (int i=0; i < 5; i++)
int A[ ] = {5, 10, 12, 15, 4}; A[i] : value of element A[i]
cout<<&A[i]<<“ “<<A[i]<<endl;
cout<<"Address Contents\n";
for (int i=0; i < 5; i++)
cout<<"Address Contents\n"; A+i : address of element A[i]
cout<<&A[i]<<" "<<A[i]<<endl;
for (int i=0; i < 5; i++)
return 0; *(A+i) : value of element A[i]
cout<<A+i<<“ “<<*(A+i)<<endl;
}
&A[i] : address of element A[i]
A[i] : value of element A[i] /* print the address of 1D array by using pointer */
int *ptr = A;
Result in turboC cout<<"Address Contents\n"; ptr+i : address of element A[i]
(sizeof(int)=2) for (int i=0; i < 5; i++) *(ptr+i): value of element A[i]
Memory Location(A[i]) = start_address + W*i
Address Contents
cout<<ptr+i<<“ “<<*(ptr+i)<<endl;

5 10 12 15 4 65516 5
cout<<"Address Contents\n";
65518 10
65520 12 for (int i=0; i < 5; i++) &ptr[i] : address of element A[i]
65522 15 cout<<&ptr[i]<<“ “<<ptr[i]<<endl; ptr[i] : value of element A[i]
65524 4 }
start_address=6487536

Example: Write C++ program to print address of each element in a 1D-array Example
#include <iostream>
Write C program to print address of each element in a 1D-array:
using namespace std;
int main()
#include <stdio.h>
{ int A[ ] = {5, 10, 12, 15, 4};
int main()
cout<<"Address Contents\n";
&A[i] : address of element A[i] { int A[ ] = {5, 10, 12, 15, 4};
for (int i=0; i < 5; i++)
A[i] : value of element A[i] printf("Address Contents\n");
cout<<&A[i]<<“ “<<A[i]<<endl;
for (int i=0; i < 5; i++)
&A[i] : address of element A[i]
printf("%8d %5d\n", &A[i], A[i]); A[i] : value of element A[i]
cout<<"Address Contents\n"; A+i : address of element A[i]
for (int i=0; i < 5; i++)
*(A+i) : value of element A[i]
cout<<A+i<<“ “<<*(A+i)<<endl;
printf("Address Contents\n");
for (int i=0; i < 5; i++) A+i : address of element A[i]
/* print the address of 1D array by using pointer */
int *ptr = A;
printf("%8d %5d\n", A+i, *(A+i)); *(A+i) : value of element A[i]
cout<<"Address Contents\n"; ptr+i : address of element A[i]
for (int i=0; i < 5; i++) *(ptr+i): value of element A[i]
/* print the address of 1D array by using pointer */
cout<<ptr+i<<“ “<<*(ptr+i)<<endl;
int *ptr = A;
printf("Address Contents\n");
cout<<"Address Contents\n"; ptr+i : address of element A[i]
for (int i=0; i < 5; i++) &ptr[i] : address of element A[i] for (int i=0; i < 5; i++)
*(ptr+i) : value of element A[i]
cout<<&ptr[i]<<“ “<<ptr[i]<<endl; ptr[i] : value of element A[i] printf("%8d %5d\n", ptr+i, *(ptr+i));

}
}
Printing an array Printing an array
void print_array(int a[], int len) {
for (int i=0;i<len;i++)
cout << "[" << i << "] = "
<< a[i] << endl;
}

void print_array(int *a, int len) {


for (int i=0;i<len;i++)
cout << "[" << i << "] = "
<< *a++ << endl;
}
 For clarity, use array notation instead of pointer notation when manipulating
arrays.

21 22

Contents 4. Pointer arithmetic


1. Getting the Address of a Variable int a[] = {4,7,11,5,23}; int *ptr = a;

2. Pointer Variables Operation Example


++, -- ptr++; // points at 7
3. The Relationship Between Arrays and Pointers ptr--; // now points at 4
+, - (pointer and int) cout << *(ptr + 2); // 11
4. Pointer Arithmetic +=, -= (pointer and ptr = a; // points at 4
5. Initializing Pointers int) ptr += 2; // points at 11
- (pointer from pointer) cout << ptr – a;
6. Pointers as Function Parameters //difference (number of ints) between ptr and val
7. Pointer to constants
<, <=, >, >=, … //compare address in pointers
8. Dynamic Memory Allocation if(ptr1<ptr2) …
==, != if(ptr1 == ptr2)… //compare addresses
if(*ptr1 == *ptr2)… //compare contents
23 24
const int SIZE = 8; #include <iostream>
int set[SIZE] = {5, 10, 15, 20, 25, 30, 35, 40}; using namespace std;
int *numPtr; // Pointer const int MAX = 100;
int count; // Counter variable for loops
int main()
// Make numPtr point to the set array. {
numPtr = set; int numbers[MAX]; // Array of integers
// Use the pointer to display the array contents. int SIZE; // Size of the array
cout << "The numbers in set are:\n"; int count; // Counter variable
for (count = 0; count < SIZE; count++)
{
cout << *numPtr << " "; cout << “Size of the array = “; cin>>SIZE;
numPtr++; for (count = 0; count < SIZE; count++)
} // Get a value to store in numbers[count].
// Use pointer notation instead of subscripts.
// Display the array contents in reverse order. (1)
cout << "\nThe numbers in set backward are:\n"; cout << "Here are the numbers you entered:\n";
for (count = 0; count < SIZE; count++) for (count = 0; count < SIZE; count++)
{ // Display a value of the array.
numPtr--; // Use pointer notation instead of subscripts.
cout << *numPtr << " "; (2)
} cout << endl;
return 0; return 0;
} 25 } 26

#include <iostream>
using namespace std;
const int MAX = 100;
Arrays as Function Arguments
• When an entire array is passed to a function, it is not passed by value, but passed by
int main()
reference.
{
int numbers[MAX]; // Array of integers – Imagine the CPU time and memory that would be necessary if a copy of a
int SIZE; // Size of the array 10,000-element array were created each time it was passed to a function!
int count; // Counter variable Instead, only the starting memory address of the array is passed.
int *ptr = numbers;  Changes made to array in a function are reflected in actual array in calling function
cout << “Size of the array = “; cin>>SIZE;
for (count = 0; count < SIZE; count++)
// Get a value to store in numbers[count].
// Use pointer notation instead of subscripts.
(1) cin >> ptr[count];
cout << "Here are the numbers you entered:\n"; for (int index=0; index < ARRAY_SIZE; index++)
for (count = 0; count < SIZE; count++) cout<<numbers[index]<<“ “;
// Display a value of the array.
// Use pointer notation instead of subscripts.
(2) cout << ptr[count];
cout << endl;
return 0; for (int index=0; index < size; index++)
} 27 nums[index]*=2; 28
Exercise Exercise: Array version
 Write a program that includes the following functions:
 Input values for an array
 Increase all values of the array by 2
 Print out an array
 You should use pointers to access the array. The array is
passed as function parameters
Array version:
void input_array(int a[], int len);
void change_array(int a[], int len);
void print_array(int a[], int len);
Pointer version:
void input_arrayP(int *a, int len);
void change_arrayP(int *a, int len);
void print_arrayP(int *a, int len);
29 30

Contents 5. Initializing Pointers


1. Getting the Address of a Variable • Can initialize at definition time:
int num, *numptr = &num; int num;
2. Pointer Variables int a[5], *ptr = a; int *numptr;
numptr =&num;
3. The Relationship Between Arrays and Pointers
4. Pointer Arithmetic • Cannot mix data types:
double cost;
5. Initializing Pointers int *cptr = &cost; //won’t work: because ????
6. Pointers as Function Parameters the type of “cost” is double, while “cptr” is the pointer to an
“int” (it is used to store address of variable with type of “int”)
7. Pointer to constants
8. Dynamic Memory Allocation • Can test for an invalid address for a pointer with:
if (!cptr) . . .

31 32
Contents 6. Pointers as Function Parameters
• A pointer can be a parameter
1. Getting the Address of a Variable
• Works like reference variable to allow change to argument from within function
2. Pointer Variables • Requires:
– asterisk * on parameter in prototype and heading:
3. The Relationship Between Arrays and Pointers void getNum(int *ptr); //ptr is pointer to an int
4. Pointer Arithmetic – asterisk * in body to deference the pointer (~access the object that the pointer points
to):
5. Initializing Pointers cin >> *ptr;
– address as argument to the function:
6. Pointers as Function Parameters getNum(&num); //pass address of num to function getNum

7. Pointer to constants
8. Dynamic Memory Allocation

33 34

Example 1 Example 2
void swap(int *x, int *y){ void swap(int x, int y){ // This program uses two functions that accept addresses of
//swap the contents pointed int temp = x; // variables as arguments.
//by pointers x and y: x = y; #include <iostream>
int temp = *x; y = temp; using namespace std;
*x = *y; }
*y = temp; int main(){ // Function prototypes
} int num1 = 2, num2 = 3; void getNumber(int *);
int main(){ void doubleValue(int *);
swap(num1, num2);
int num1 = 2, num2 = 3; }
int main()
//pass address of num1 and num2
{ int number;
//to function swap:
swap(&num1, &num2);
// Call getNumber and pass the address of number.
}
getNumber(&number);
• In pass-by-reference: the function
receives a direct link to the original // Call doubleValue and pass the address of number.
variable, so any changes made within doubleValue(&number);
the function do modify the original.
• In pass-by-value: a copy of the // Display the value in number.
variable's value is sent to a function, so cout << "That value doubled is " << number << endl;
any changes made to it within the return 0;
function do not affect the original 35
} 36
variable.
Example 2 Contents
//***************************************************************
// Definition of getNumber. The parameter, input, is a pointer. * 1. Getting the Address of a Variable
// This function asks the user for a number. The value entered *
// is stored in the variable pointed to by input. * 2. Pointer Variables
//***************************************************************

void getNumber(int *input)


3. The Relationship Between Arrays and Pointers
{
cout << "Enter an integer number: ";
4. Pointer Arithmetic
}
cin >> *input;
5. Initializing Pointers
//***************************************************************
6. Pointers as Function Parameters
// Definition of doubleValue. The parameter, val, is a pointer. *
// This function multiplies the variable pointed to by val by * 7. Pointer to pointer
// two. *
//***************************************************************

void doubleValue(int *val)


{
*val *= 2;
} 37 38

6. Pointer to pointer (double pointer) 6. Pointer to pointer (double pointer)


• Double pointers are those pointers which stores the address of another int var = 10;
pointer: //Pointer to int
int *ptr1 = &var;
– The first pointer is used to store the address of the variable,
// Pointer to pointer (double pointer)
– The second pointer is used to store the address of the first pointer.
int **ptr2 = &ptr1;

#include <stdio.h>
int main() {
int var = 10;
//Pointer to int
int *ptr1 = &var;
// Pointer to pointer (double pointer)
int **ptr2 = &ptr1;
printf("var: %d\n", var);
printf("*ptr1: %d\n", *ptr1);
printf("**ptr2: %d", **ptr2);
return 0;
39 40
}
6. Pointer to pointer (double pointer) Contents
Declaration: A double pointer can be declared similar to a single pointer. The 1. Getting the Address of a Variable
difference is we have to place an additional ‘*’ before the name of the pointer.
type **name; 2. Pointer Variables
Initialization: The double pointer stores the address of another pointer to the 3. The Relationship Between Arrays and Pointers
same type.
name = &single_ptr; // After declaration
4. Pointer Arithmetic
type **name = &single_ptr; // With declaration
5. Initializing Pointers
Deferencing: To access the value pointed by double pointer, we have to use the
dereference operator * two times. 6. Pointers as Function Parameters
*name; //Gives the address of the single pointer 7. Pointer to constants
**name; //Gives the value of the variable it points to
8. Dynamic Memory Allocation

41 42

7. Pointers to Constants 7. Pointers to Constants


We can store the address of a constant in a pointer
Example:
const int SIZE = 6;
const double b[SIZE] = {18.4, 17.4, 12.8, 14.7, 20.0, 18.9};

• Ptr is an array of constant doubles:


void displayB(const double *Ptr, int size)
{ This is what Ptr points to
for(int count=0; count<size; count++)
cout << *(Ptr + count) << endl;
}
The parameter, Ptr, is a pointer to const double

43 44
Constant Pointers Constant Pointers to Constants
• A constant pointer is a pointer that is initialized with an address, • A constant pointer to a constant is:
and cannot point to anything else. – a pointer that points to a constant
• Example: – a pointer that cannot point to anything except what it is
int value = 22; pointing to
Example:
* const indicates that ptr is a constant pointer int value = 22;

int * const ptr = &value;


* const indicates that ptr is a constant pointer
This is what ptr points to
const int * const ptr = &value;
This is what ptr points to

45 46

Contents MEMORY MANAGEMENT


1. Getting the Address of a Variable STATIC MEMORY:
• Until now, we have only learned about static memory
2. Pointer Variables • Memory is allocated at compilation time
3. The Relationship Between Arrays and Pointers • Declaration of large memory variables (arrays) must be determined
before the program is compiled.
4. Pointer Arithmetic • int students[10];
• what if we don’t know the exact number of students in advance?
5. Initializing Pointers
6. Pointers as Function Parameters DYANMIC MEMORY:
• We can “ask” for memory while the program is running.
7. Pointer to constants
• We can allocate and release memory ourselves!
8. Dynamic Memory Allocation • More powerful programming ability (also more potential for
errors!)

47
Memory Allocation Conceptual View of Memory

int a[200]; int *ptr;


(DYNAMIC MEMORY)
ptr = (int*) malloc(200*sizeof(int));
int *ptr = a; …
… free(ptr);

int *ptr = new int[200];


C++ …
delete [] ptr;

8. Dynamic Memory Allocation 8. Dynamic Memory Allocation


• Uses malloc to allocate memory OR Uses new operator in C++ To allocate array: Operating System
int *iptr;
//Allocate memory for a single integer: Manages dynamic
iptr =(int*) malloc(sizeof(int)); OR: iptr = new int; memory.
You have:
It returns address of memory location. Ask OS to find a segment
int *p; Of memory of 1000*4 btyes
Note: The memory may not have been allocated successfully. So it is
good to check if new operator is returning NULL pointer and take p = new int[1000];
appropriate action as below: OS returns
the address.
int *iptr = NULL;
iptr =(int*) malloc(sizeof(int)); //iptr = new int; So, you need a pointer to the type you requested.
if(iptr == NULL) { If you request <int>, you need an <int> pointer.
cout << "Error: out of memory." <<endl;
If you request <float>, you need a <float> pointer.
exit(1);
}

51
Allocating memory using “new” 8. Dynamic Memory Allocation
• Uses malloc operator to allocate memory:

C
double *iptr;
int *p; new returns the address to the iptr = (double*) malloc(sizeof(double));
“start” of the memory it allocated
p = new int[7]; //allocate mem for 7 integers • To allocate array:
//p is assigned 8002 8002 p[0] int *arrayPtr = (int*) malloc(100 * sizeof(int));

8006 p[1]
• Uses new operator to allocate memory:
8010 p[2]
C++
p[0] = *(p) = *(p+0) = ? double *iptr;
8014 iptr = new double;
p[1] = *(p+1) = ?
• To allocate array:
8018
p[2] = *(p+2) = ? int *arrayPtr = new int[100];
8022 • To access array:
8026 for(i=0;i<100;i++)
arrayPtr[i]=i*i; //or *(arrayPtr+i)=i*i;
• Program will terminate if not enough memory available to allocate 54

Releasing Dynamic Memory Memory Leak Problem


• Use free to free dynamic memory: • Make sure to delete memory when finished
free(iptr);
• Use free to free dynamic array:
C int *p;

free(arrayPtr); p = new int[100]; 100 integers

int a;
• Use delete to free dynamic memory:
C++
a

delete iptr;
• Use [] to free dynamic array:
p = &a;
delete [] arrayPtr; NO ONE HAS ACCESS TO THIS MEMORY 100 integers

This memory is un-addressable


And it is reserved until your
After delete is called on a memory region, that region should no longer a program terminates. It is
garbage
be accessed by the program. (it has leaked from the system)
55
Example: Need an array of unknown size
int main()
{
cout << “How many students? “; cin >> n;

int *grades = new int[n];

for( int i = 0; i < n; i++)


{
cout << “Input Grade for Student” << (i+1) << “ ? :”;
cin >> grades[i] ;
}
// call a function with dynamic array:
printMean( grades, n );
//Free dynamically allocated memory:
delete [] grades;
grades = 0; //makes grades point to NULL
Prevent code from using the pointer to access the area of memory that was freed.
return 0;
}

You might also like