Non-Primitive Data Types and Pointers

User-Defined Ordinal Types

Enumeration types

Ø  Enumeration types are used to create data types whose constant data are identifiers in C++, C#, Java, etc.

Ø  Each identifier (constant data) in the set of values is assigned an integer value.

Ø  When an expression is evaluated, each identifier (constant data) in that expression is replaced by its value.

Examples in C/C++/C#:

enum Days {Mon, Tue, Wed, Thu, Fri, Sat, Sun}; // Mon = 0, Tues = 1, . . ., etc.

Days today,

yesterday = Wed;

today = yesterday + 1;

enum Colors {red = 1, blue = 1000, green = 10000};

Colors CarColor;

Days oneDay;

cout < endl < “enter a car color: 1 for red, 1000 for blue, 10000 for green:\t”;

cin > CarColor;

if (CarColor != red & CarColor != blue & CarColor != green)

cout < endl < “invalid car color”;

cout < endl < “enter a day of the week code: 0 – 6 :\t”;

cin > oneDay;

if (oneDay < Mon || oneDay > Sun)

cout < endl < “invalid day code”;

/*---- read the 5-day deposits to a bank by a store into the array deposits [ ] ------*/

double deposits [5];

for (days dayNdx = Mon; dayNdx <= Fri; dayNdx ++)

{

cout < endl < “enter deposit for day:\t” < dayNdx + 1;

cin > deposits [(int)dayNdx];

}


Subrange Types

Ø  A subrange type is used to define a range of values of an ordinal type in Pascal and Ada.

Example (in Ada):

subtype arrayindex is integer range 1 . . 100;

-- define arrayindex as a data type with values 1 - 100

i : arrayindex;

-- defines variable i with data type arrayindex (it can only have values from 1 to 100)

Reference Types

Ø  A reference type is used in C++ to associate two different names to the same memory location. It is used primarily for parameters in function definitions.

Example

int main( )

{

int robert = 5;

int bob = &robert;

bob ++;

cout < endl < “robert=” < robert < “\tbob=” < bob;

robert += 2;

cout < endl < “robert=” < robert < “\tbob=” < bob;

return 0;

}

Output:

robert= 6 bob= 6

robert= 8 bob= 8

Reference Parameters

Example using value and reference parameters (in C++)

void funct1 (int vnum , int &ref1 , int &ref2)

{

vnum += 7;

ref1 += 4;

ref2 = vnum + ref1;

}


int main( )

{

int num1 = 5, num2 = 16 , num3;

funct1 (num1 , num2 , num3);

cout < endl < “num1=” < num1 < “\tnum2=” < num2 < “\tnum3=” < num3;

return 0;

}

This function call is executed as follows:

funct1 (num1 , &num2 , &num3);

{

vnum = 5;

vnum += 7;

num2 += 4;

num3 = vnum + num2;

}

The output of this program is: num1= 5 num2= 20 num3 = 32

Pointer Types

Ø  A pointer type is used to create a memory location (variable) to hold the address of another memory location.

Ø  A pointer type is available in C++ but not in Java.

Example (in C++)

int main( )

{

int num = 5,

*pt;

pt = &num;

*pt += 3;

cout < endl < “num=” < num < “\t*pt=” < *pt;

num += 2;

cout < endl < “num=” < num < “\t*pt=” < *pt;

return 0;

}

Output:

num= 8 *pt= 8

num= 10 *pt= 10

Pointer Parameters

Example using value and pointer parameters (in C++)

void funct1 (int vnum , int * pt1 , int * pt2)

{

vnum += 7;

*pt1 += 4;

*pt2 = vnum + *pt1;

}

int main( )

{

int num1 = 5, num2 = 16 , num3;

funct1 (num1 , &num2 , &num3);

cout < endl < “num1=” < num1 < “\tnum2=” < num2 < “\tnum3=” < num3;

return 0;

}

This function call is executed as follows:

funct1 (num1 , &num2 , &num3);

{

vnum = 5;

pt1 = &num2;

pt2 = &num3;

vnum += 7;

*pt1 += 4;

*pt2 = vnum + *pt1;

}

The output of this program is: num1= 5 num2= 20 num3 = 32


Array Types

Need to consider the following issues:

·  What are the possible data types of the elements of an array?

·  What are the possible data types of the indexes (or subscripts) of an arrays?

·  How to specify the subscripting expression of an array element?

·  What are the possible ranges of the subscript or index of an array?

·  Are subscripting or indexing expressions values checked to find out if they are in the range of values of the array index?

·  How many subscripts are allowed?

·  How do you define/declare an array?

·  Array initialization.

·  How are arrays implemented?

·  Array operations

·  Can an array be a return type of a function?

·  Arrays as parameters to procedures/methods/functions.

Possible Data Types of the Elements of an Array in C++

Ø  In C++ the possible data types of the elements of an array are any basic data type, structures (struct), classes, pointers, and unions data types.

Examples:

char letters [10]; // array of characters

double payRates [100]; // array of double precision values

int * valueptrs [ 20 ]; // array of pointers to hold the addresses of integer variables

struct Employee {

string name;

int hours;

double payRate;

};

Employee employeeList [150]; // array of structure Employee

Possible Data Types of the Array Indexes

Ø  In most programming languages, an array subscript data type is a sub-range of integers.

Ø  But Pascal and Ada also allow some other data types such as Boolean, character, and enumeration types.

Ø  In Pascal, C/C++ and Java, indexing expressions are specified within the brackets.

Examples: cout < list [ i ]; value1 [j + 5] = num + j;

Ø  In FORTRAN, they are specified within the parentheses.

Range of an Index

Ø  In C/C++, and Java, the range of the index is 0 to size -1 (where size is the number of the elements).

Ø  In FORTRAN 90, it is by default 1 to size.

Ø  In most other languages, subscript ranges must be specified by the programmer when the array is defined.

For example, in Pascal we have the following declarations:

var list1, list2 : array [10 . . 50] of integer; /* the subscript range is from 10 to 50 */

Index Range Checking

Ø  C/C++ and FORTRAN do not check subscripts for the range

Ø  but Pascal, Ada, and Java do.

Number of Subscripts in Arrays

Ø  In FORTRAN, the maximum number of indexes is seven.

Ø  In C/C++ and Java, there is no limit in the number of subscripts. But an array with more than one subscript is a one dimensional array whose elements are also arrays.

For example in C++, int mat [5] [4];

defines an array of 5 elements, with each element an array of 4 integers.

Arrays Declaration

Ø  In C/C++ an array is declared as follows: <data type> <array-name> [ size ];

Examples: int list [100];

Ø  In Java an array is an explicit heap-dynamic variable: after the user has declared an array variable, he/she must use the new operator to allocate memory locations for its members in the heap as follows:


<data type> [ ] <array-name> = new <data type> [size];

Or

<data type> [ ] <array-name>;

<array-name> = new <data type> [size]; // initialization

Examples: int [ ] list = new int [100];

Or

int [ ] list;

list = new int [100];

Ø  Fortran 95 and C# also support fixed heap-dynamic arrays.

Ø  In Pascal an array is declared as follows:

<array-name> : array [low-bound . . high-bound] of <data type>;

Example: var list : array [10 . . 50] of integer;

Array Initialization

Ø  In C/C++, Java, ada, Pascal, and C#, an array may be initialized when it is defined.

Example in Java, the new operator is not needed when an array is initialized as follows:

int [ ] smallprimes = {2, 3, 5, 7, 11, 13};

Operations on Arrays

Ø  Elemental array operations are provided in FORTRAN (assignment, arithmetic and logical operations).

Ø  But C/C++, and Java do not have operations on arrays.


Can an Array be a Return Type of a Function?

Ø  An array may be a return type of a method in Java, but not in C/C++.

Example:

import java.util.Scanner;

public class ProcessTestScores

{

public static void main ( String [ ]args )

{

double [ ] scoreList;

/*------read 20 test scores ------*/

scoreList = readTestScores( 20 );

/*------compute and print the average test score ------*/

double total = 0;

for (i = 0 ; i < 20 ; i++)

total += scoreList[ i ];

System.out.println(“The average test score is:\t” + total/20);

return 0;

}

/*------read test scores and place them into an array ------*/

static double [ ] readTestScores( int size )

{

Scanner input = new Scanner( System.in );

double [ ] list = new double [ size ];

/*------read the test scores ------*/

for (i = 0 ; i < size ; i++)

list [ i ] = input.nextDouble( );

return( list );

}

}


Passing an Array to a Function/Method/Procedure

Ø  You pass an array to a function in C++ by just passing the address of the first element of that array to it: that means the name of the array.

Ø  In addition to passing the address of the first element of the array, you must also pass to the function the size of the array so that it knows how many elements are in the array.

Ø  The parameter that corresponds to an array argument is specified in a function header as follows:

©2017 Gilbert Ndjatou Page 1

<data-type> <Parameter-name>[ ]

The following are examples of functions with array(s) as parameters:

/*------function readvalues() ------*/

/* read values into an array of integer */

void readValue(int list[ ], int size)

{

for(int j = 0; j < size; j++)

{

cout “\nEnter a value:\t”;

cin list[ j ];

}

}

/*------function computeAverage()------*/

/* compute the average of the elements of an array and return it */

double computeAverage(double scores[ ], int size)

{

double total = 0;

/*------compute the total of all elements ------*/

for(int j = 0; j < size; j++)

total += scores[j];

/*------compute and return the average ------*/

return ( total / size );

}

/*------function addlist ------*/

/* add a value to each element of an array and build a new one */

void addlist(int list1[ ], int list2[ ], int num, int size)

{

for(int j = 0; j < size; j++)

list2[j] = list1[j] + num;

}

Pointer Arithmetic and Array Implementation in C/C++

Ø  If pt is a pointer variable that contains the address of a memory location with size size, and a is a positive integer constant, then the expression:

pt + a holds the address: pt + a * size and

pt – a holds the address: pt – a * size (when pt – a * size is positive)

Ø  A pointer may be initialized to 0 or NULL (symbolic constant defined in the header file iostream).

Ø  A pointer with the value 0 or NULL is known as the null pointer and cannot be used to reference a memory location.

Example

Given the following definitions of arrays letters and idlist with their memory representations:

char letters[5];

int idlist[5];

Memory

letters

Addresses: 2000 2001 2002 2003 2004

letters letters +1 letters +2 letters +3 letters + 4

letters[0] letters[1] letters[2] letters[3] letters[4]

idlist

Addresses: 2300 2304 2308 2312 2316

idlist idlist + 1 idlist + 2 idlist + 3 idlist + 4

idlist[0] idlist[1] idlist[2] idlist[3] idlist[4]

We have the following:

Letters + 1 = = 2001 letters + 2 == 2002 letters + 3 = = 2003 letters + 4 = = 2004

idlist + 1 = = 2304 idlist + 2 = = 2308 idlist + 3 = = 2312 idlist + 4 = = 2316

Ø  The elements of an array can be accessed either by using indexed variables or by using pointer arithmetic.


Example

/*------code segment to read the values into the array letters[ ] by using pointer arithmetic ------*/

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

cin > *(letters + i) ;

/*------code segment to read the values into the array idlist[ ] by using pointer arithmetic ------*/

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

cin > *(idlist + i) ;

/* code segment to write the elements of array letters in reverse order by using pointer arithmetic */

for( char *pt = letters + 4 ; pt > = letters ; pt - - )

cout < *pt ;

Dynamic Arrays (in C++)

Ø  A dynamic array is a sequence of consecutive memory locations allocated in the heap by using the new operator.

Ø  You allocate a dynamic array as follows:

<type-pointer> = new <type> [ size ];

Where <type> is any valid data type and size is the number of memory locations to be allocated.

Ø  The new operator returns the address of the first of the memory locations allocated.

Example

The elements of a dynamic array to hold 5 character values are created as follows:

char * cpt;

cpt = new char [ 5 ];

cpt

Addresses 145 146 147 148 149