Presentation is loading. Please wait.

Presentation is loading. Please wait.

Programming Reviews Lecture 1 Lecture Objectives What is Data Structure? What are Algorithms? To revise the use of pointers in relation to arrays To.

Similar presentations


Presentation on theme: "Programming Reviews Lecture 1 Lecture Objectives What is Data Structure? What are Algorithms? To revise the use of pointers in relation to arrays To."— Presentation transcript:

1

2 Programming Reviews Lecture 1

3 Lecture Objectives What is Data Structure? What are Algorithms? To revise the use of pointers in relation to arrays To revise the use of classes with pointers To revise the use of dynamics arrays

4 What is Data Structure & Algorithms? Simple definition : Data Structure - A data object that can store more than one data value at a time, such as an array or record. Algorithm - A set of instructions that accomplish a given task. - A precisely specified procedure for solving a problem. Program Implementation of algorithm in programming language

5 Definition from Dictionary of Algorithms and Data Structures (National Institute of Standards & Technology, USA) http://www.nist.gov/dads/ Algorithm A computable set of steps to achieve a desired result. Note: The word comes from the Persian author Abu Ja'far Mohammed ibn Mûsâ al-Khowârizmî who wrote a book with arithmetic rules dating from about 825 A.D. [ In Latin, al-Khowârizmî became Algorismus ]

6 Definition from Dictionary of Algorithms and Data Structures (National Institute of Standards & Technology,USA) http://www.nist.gov/dads/ Data Structure An organization of information, usually in memory, for better algorithm efficiency, such as queue, stack, linked list, heap, dictionary, and tree, or conceptual unity, such as the name and address of a person. It may include redundant information, such as length of the list or number of nodes in a subtree. Note: Most data structures have associated algorithms to perform operations, such as search, insert, or balance, that maintain the properties of the data structure.

7 Review : Fundamentals of Pointers Arithmetic p + i&p[i] is equivalent *(p + i)p[i] is equivalent Given a pointer or an array p of any data type and i an integer : Thus also: You need to be absolutely sure about this !!!! p is equivalent *p &p[0] p[0]

8 1100 1520 [ int* ] 1100 [int] 341 1104 [int] 157 1108 [int] 31 1112 [int] 682 p p + 1 p + 2 p + 3 p is equivalent *p &p[0] p[0] p+1 is equivalent *(p+1) &p[1] p[1] p+2 is equivalent *(p+2) &p[2] p[2]

9 ... int m[5], n[10]; int *p; p = m; p = n; m = n;... Even though we can treat pointer as array, pointers and arrays are actually not the same. valid invalid !!!

10 Review : Static Arrays vs. Dynamic Arrays int main() { int m[5],i=0; do { cin >> m[i]; if (i==4) { cout << "array is full !!"; exit(1); } } while ( m[i++] != -1 ); } Static Memory Allocation : The size of arrays must be determined during compile time and our program can not change the size of the arrays. Static Array :

11 int main() { int size = 5; int m[size];... } Static Array : int main() { const int size = 5; int m[size];... } INVALID !!! Valid

12 Dynamic Memory Allocation : int *p; p = new int; *p = 47; 1432 p [ int* ] 47 Allocate dynamically a single integer : delete p; 1432 p [ int* ] De-allocate the dynamically allocated integer :

13 Dynamic Memory Allocation : int *q; q = new int[4]; for (int i=0;i<4;i++) q[i] = i*2; 1452 q [ int* ] 0 Allocate dynamically an integer array : delete [] q; 1452 q [ int* ] De-allocate the dynamic integer integer : 42 6 NOTE : it is a good practice to set the pointer to NULL (or value 0) after the de-allocation this is operator delete[] and it is different from operator delete. this is operator new[] and it is different from operator new.

14 class Dummy { public: Dummy() { cout << "dummy constructed\n"; } void greet() { cout << "I am a dummy !\n"; } ~Dummy() { cout << "dummy destructed\n"; } }; int main() { Dummy* p; p = new Dummy; p->greet(); delete p; return 0; } Dynamic Memory Allocation and Objects : (using C++ operator new and delete) dummy constructed I am a dummy ! dummy destructed output: operator new allocate memory for one instance of class Dummy and then invoke the default constructor of class Dummy. operator delete first invoke the destructor of class Dummy and then de-allocate the memory allocated for it by operator new.

15 class Dummy { public: Dummy() { cout << "dummy constructed\n"; } void greet() { cout << "I am a dummy !\n"; } ~Dummy() { cout << "dummy destructed\n"; } }; int main() { Dummy* p; p = (Dummy*) malloc ( sizeof(Dummy) ); p->greet(); free (p); return 0; } For comparison, if we use the malloc() and free() function of C : I am a dummy ! output: Memory is being allocated, but the constructor of class Dummy is not being called. Memory is de-allocated (freed) but destructor of class Dummy is not being called. Unpredictable behavior as the object is never being constructed. DO NOT use malloc() and free() in C++ !!! Always use operator new and delete instead.

16 class Dummy { public: Dummy() : name ("NoBody") { cout << "dummy constructed\n"; } Dummy(string Name) : name (Name) { cout << "alternatively constructed\n"; } void greet() { cout << "I am at" << name << "!\n"; } ~Dummy() { cout << "dummy destructed\n"; } private: string name; }; int main() { Dummy* p; p = new Dummy (“Al-Albyt University"); p->greet(); delete p; return 0; } Invoke constructor in dynamically allocated object : alternatively constructed I am at Al-Albyt University dummy destructed output: operator new allocates memory for one instance of class Dummy and then invoke the alternative constructor (which accept a string) of class Dummy.

17 class Dummy { public: Dummy() : name ("Nobody") { cout << "c "; } Dummy(string Name) : name (Name) { cout << "alternatively constructed\n"; } void greet() { cout << "I am " << name << "!\n"; } ~Dummy() { cout << "d "; } private: string name; }; int main() { Dummy* p; p = new Dummy[4]; for (int i=0;i<4;i++) p[i].greet(); delete [] p; return 0; } c c c c I am NoBody! I am Nobody! d d output: operator new[] allocate memory for 4 instances of class Dummy and then invoke the default constructor of each of the instances of class Dummy. Constructor and dynamically allocated array : operator delete[] de-allocate memory allocated earlier by operator new[], the destructors of each instances are being called before memory de- allocation.

18 #include using namespace std; class MyArray { public: MyArray() : capacity(4), size(0) { data = new int[capacity]; } void add(int n) { if (size==capacity) increaseCapacity(); data[size] = n; size++; } int get(int index) { return data[index]; } void set(int index, int value) { data[index] = value; } void display() { for (int i=0;i<size;i++) cout << data[i] << " "; } private: void increaseCapacity() { capacity *= 2; int* newdata = new int[capacity]; for (int i=0;i<size;i++) newdata[i] = data[i]; delete[] data; data = newdata; } int* data; int size, capacity; }; int main() { MyArray m; for (int i=0;i<10;i++) m.add(i*2); m.display(); } 0 2 4 6 8 10 12 14 16 18 output: Resizable dynamic array :

19 int numOfRobots = 10; Robot* robot; robot = new Robot[numOfRobots];... delete[] robot; robot = NULL;... One-Dimensional Dynamic Array :

20 #include using namespace std; int main() { if ("Ali" > "ali") cout << "good" ; else if ("Ali" == "ali") cout << “not good" ; else cout << “thanks"; int i; cin >> i; } thanks

21 Review : 2-dimensional Dynamic Arrays int noOfRows,noOfCols; int **q; cout "; cin >> noOfRows >> noOfCols; q = new int * [noOfRows]; for (int i=0; i<noOfRows; i++) q[i] = new int[noOfCols]; for (int i=0; i<noOfRows;i++) for (int j=0; j<noOfCols;j++) q[i][j] = i*i+j; for (int i=0; i<noOfRows;i++) { for (int j=0; j<noOfCols;j++) cout << setw(3) << q[i][j]; cout << endl; } for (int i=0;i<noOfRows;i++) delete[] q[i]; delete[] q; 2-D dynamic array with equal number of columns for each rows : Input => 5 4 0 1 2 3 1 2 3 4 4 5 6 7 9 10 11 12 16 17 18 19 sample run: Make sure the allocation and deallocation sequences are correct !!!

22 Review : List of Pointers struct Student { void set(string Name,float Mark) { name = Name; mark = Mark; } void display() { cout << name << ": " << mark << endl; } string name; float mark; }; class StudentList { public: StudentList(int NumOfStud=5) : numOfStud(NumOfStud) { student = new Student [numOfStud]; } ~StudentList() { delete[] student; } void set(int Index,string Name,float Mark) { student[Index].set(Name,Mark); } void sortAccordingToNames(); void display(); private: int numOfStud; Student *student; }; Consider the struct Student as a data structure to store a single record of student. Consider the class StudentList as a data structure to store records of students. struct is similar to class except that the members has default access privilege of public. continue... to be defined next slides

23 void StudentList::sortAccordingToNames() { for (int i=0;i<numOfStud;i++) for (int j=numOfStud-1;j>=i+1;j--) if ( student[j-1].name > student[j].name ) { string nametemp = student[j-1].name; student[j-1].name = student[j].name; student[j].name = nametemp; float marktemp = student[j-1].mark; student[j-1].mark = student[j].mark; student[j].mark = marktemp; } void StudentList::display() { for (int i=0;i<5;i++) student[i].display(); }...continue records are sorted by considering the name of each record every fields in each record are swapped to be sorted positions. display all the records stored in the dynamic array.

24 int main() { StudentList studlist(5); studlist.set(0,"John",10); studlist.set(1,"Chong",60); studlist.set(2,"Zul",50); studlist.set(3,"Ali",100); studlist.set(4,"Samy",95); cout << "--- original list ---" << endl; studlist.display(); studlist.sortAccordingToNames(); cout << "--- sorted list ---" << endl; studlist.display(); return 0; }...continue --- original list --- John: 10 Chong: 60 Zul: 50 Ali: 100 Samy: 95 --- sorted list --- Ali: 100 Chong: 60 John: 10 Samy: 95 Zul: 50 sample run: If you notice, in the StudentList::sortAccordingToNames() function, all the fields in the student record are moved/swapped around until the whole list is sorted. This don't seems to be efficient if the student record contains a lot of fields. In the next few slides, we consider a more efficient way to achieve the same results.

25 struct Student {... //same as before }; class StudentList { public: StudentList(int NumOfStud=5) : numOfStud(NumOfStud) { student = new Student [numOfStud]; index = new int [numOfStud]; for (int i=0;i<numOfStud;i++) index[i] = i; } ~StudentList() { delete[] student; delete[] index; } void set(int Index,string Name,float Mark) {... } void display() {... } void sortAccordingToNames() {... } void displayUsingIndex(); void sortIndexAccordingToNames(); private: int numOfStud; Student *student; int *index; };...continue Revised 1 of StudentList class (with extra members) - using integer indices : same as before. extra dynamic array to keep track of indices index array initialized as 0,1,2,... and so on. to be defined next slides

26 void StudentList::displayUsingIndex() { for (int i=0;i<5;i++) student[ index[i] ].display(); } void StudentList::sortIndexAccordingToNames() { for (int i=0;i<numOfStud;i++) for (int j=numOfStud-1;j>=i+1;j--) if ( student[ index[j-1] ].name > student[ index[j] ].name ) { int indextemp = index[j-1]; index[j-1] = index[j]; index[j] = indextemp; }...continue only the indices are sorted (more efficient), NOT the actual records themselves as in the previous example. The actual order of the records are determined by the index array.

27 int main() { StudentList studlist(5); studlist.set(0,"John",10); studlist.set(1,"Chong",60); studlist.set(2,"Zul",50); studlist.set(3,"Ali",100); studlist.set(4,"Samy",95); cout <<"--- original list ---"<<endl; studlist.display(); cout <<"--- display using index ---"<<endl; studlist.displayUsingIndex(); //studlist.sortAccordingToNames(); studlist.sortIndexAccordingToNames(); cout <<"*** index array sorted ***"<<endl; cout <<"--- the current list ---"<<endl; studlist.display(); cout <<"--- display using index ---"<<endl; studlist.displayUsingIndex(); system("PAUSE"); return 0; }...continue --- original list --- John: 10 Chong: 60 Zul: 50 Ali: 100 Samy: 95 --- display using index --- John: 10 Chong: 60 Zul: 50 Ali: 100 Samy: 95 *** index array sorted *** --- the current list --- John: 10 Chong: 60 Zul: 50 Ali: 100 Samy: 95 --- display using index --- Ali: 100 Chong: 60 John: 10 Samy: 95 Zul: 50 sample run:

28 1 2 3 4 0 index[0] index[1] index[2] index[3] index[4] Samy95 Ali100 Zul50 Chong60 John10 student[0] student[1] student[2] student[3] student[4] Before the index array is being sorted 1 0 4 2 3 index[0] index[1] index[2] index[3] index[4] Samy95 Ali100 Zul50 Chong60 John10 student[0] student[1] student[2] student[3] student[4] AFTER the index array is being sorted cout << student[ index[0] ].name; cout << student[ index[1] ].name; cout << student[ index[2] ].name; cout << student[ index[3] ].name; cout << student[ index[4] ].name; Therefore, after the index array being sorted : for (int i=0;i<5;i++) cout << student[index[i]].name; OR : will produce output : AliChongJohnSamyZul Here we are actually using the integer values to ACT as pointers (even though they are not pointer in C++ sense) to the actual data (the student records) In next few slides, we will implement this using real C++ pointers.

29 struct Student {... ; class StudentList { public: StudentList(int NumOfStud=5) : numOfStud(NumOfStud) {... indexptr = new Student* [numOfStud]; for (int i=0;i<numOfStud;i++) indexptr[i] = &student[i]; } ~StudentList() {... delete[] indexptr; }... void displayUsingIndexPointer(); void sortIndexPointerAccordingToMarks(); private:... Student* *indexptr; }; dynamic array of pointers [the pointer type is Student*, i.e. pointer to Student] Each pointer points to one Student record to be defined next slides...continue Revised 2 of StudentList class (with extra members) - using pointer array : :

30 void StudentList::displayUsingIndexPointer() { for (int i=0;i<5;i++) indexptr[i]->display(); } void StudentList::sortIndexPointerAccordingToMarks() { for (int i=0;i<numOfStud;i++) for (int j=numOfStud-1;j>=i+1;j--) if ( indexptr[j-1]->mark > indexptr[j]->mark ) { Student* indexptrtemp = indexptr[j-1]; indexptr[j-1] = indexptr[j]; indexptr[j] = indexptrtemp; } only the pointers are sorted (more efficient), NOT the actual records themselves. The actual order of the records are determined by the array of pointers. for a change, here we sort according to marks rather than names....continue

31 int main() { StudentList studlist(5); studlist.set(0,"John",10); studlist.set(1,"Chong",60); studlist.set(2,"Zul",50); studlist.set(3,"Ali",100); studlist.set(4,"Samy",95); cout <<"--- original list ---"<<endl; studlist.display(); studlist.sortIndexPointerAccordingToMarks(); cout <<"*** index pointers sorted ***" << endl; cout <<"--- disp using index pointers ---" << endl; studlist.displayUsingIndexPointer(); system("PAUSE"); return 0; } --- original list --- John: 10 Chong: 60 Zul: 50 Ali: 100 Samy: 95 *** index pointers sorted *** --- disp using index pointers --- John: 10 Zul: 50 Chong: 60 Samy: 95 Ali: 100 sample run:

32 indexptr[0] indexptr[1] indexptr[2] indexptr[3] indexptr[4] Samy95 Ali100 Zul50 Chong60 John10 student[1] student[2] student[3] student[4] Before the pointer array is being sorted cout name; Therefore, after the index array being sorted : for (int i=0;i<5;i++) cout name; OR : will produce output : JohnZulChongSamyAli student[0] AFTER the pointer array is being sorted indexptr[0] indexptr[1] indexptr[2] indexptr[3] indexptr[4] Samy95 Ali100 Zul50 Chong60 John10 student[1] student[2] student[3] student[4] student[0]

33 Classes With Pointers class Person { public: Person(char Name[]="No Name") { name = NULL; setName(Name); } ~Person() { delete[] name; } void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); } void display() { cout << name << endl; } private: char* name; }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); } continue... Sharaf Manoj output: the member of this class is a pointer, this is used to create dynamic array of characters. This output is expected, however there are some potential problems in this class, what do you think?

34 class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } continue... Sharaf Manoj Ismail Manoj We may expect the output to be : added lines. is this correct?...continue ?

35 continue... Sharaf Manoj Ismail The actual output : BUT this is NOT we may be expecting !!! What is going on?...continue ? class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } added lines.

36 continue... The actual output :...continue class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } Let's trace what happened : a name b Sharaf Manoj Sharaf Manoj

37 continue... Sharaf Manoj The actual output :...continue class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } a name b Sharaf Manoj

38 continue... Sharaf Manoj The actual output :...continue class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } a name b Sharaf Manoj The value of the pointer name (which is an address) of Person a is being copied over to name of Person b.

39 continue... Sharaf Manoj The actual output :...continue class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } a name b Sharaf Manoj

40 continue... Sharaf Manoj The actual output :...continue class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } a name b Sharaf Ismail

41 continue... Sharaf Manoj Ismail The actual output :...continue class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } a name b Sharaf Ismail !

42 continue... Sharaf Manoj Ismail The actual output :...continue class Person {... void setName(char Name[]) { delete[] name; name = new char [ strlen(Name) ]; strcpy(name, Name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } ! Here is our problem : Since we did not overload the assignment operator (operator =), the compiler will create one for us which merely copy all the value from one instance of the class (in this case b) to another instance of the class (in this case a). This is called "shallow copying"

43 continue... Sharaf Manoj Ismail Manoj The actual output :...continue class Person {... Person& operator= (const Person& p) { if (this==&p) return *this; delete[] name; name = new char [ strlen(p.name) ]; strcpy(name, p.name); return *this; }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); } added function, the rest remains the same as before. This is now correct as expected !! Here, we do not merely copy the address of the dynamic character array over, but instead we delete the old array, allocate a new array with appropriate size and copy the content over, this is called "Deep copying".

44 Sharaf Manoj Ismail Manoj Ismail Norhana The actual output :...continue class Person {... Person(const Person& p) { name = new char [ strlen(p.name) ]; strcpy(name, p.name); }... }; int main() { Person a("Sharaf"), b("Manoj"); a.display(); b.display(); a = b; a.display(); b.display(); a.setName("Ismail"); a.display(); b.display(); Person c(a); c.setName("Norhana"); a.display(); c.display(); } added copy constructor CONCLUSION : For classes with pointers as members, we MUST define our own copy constructor, assignment operator (operator =) to ensure our class work properly !! The copy constructor will be called here. We should also define copy constructor !!!!


Download ppt "Programming Reviews Lecture 1 Lecture Objectives What is Data Structure? What are Algorithms? To revise the use of pointers in relation to arrays To."

Similar presentations


Ads by Google