1. Trang chủ
  2. » Công Nghệ Thông Tin

A Complete Guide to Programming in C++ part 77 doc

10 158 0

Đang tải... (xem toàn văn)

THÔNG TIN TÀI LIỆU

Thông tin cơ bản

Định dạng
Số trang 10
Dung lượng 120,03 KB

Nội dung

EXERCISES ■ 739 Exercise 1 ■ Define a function template interpolSearch() that looks up a given ele- ment in a sorted, numeric array.The array elements are of the same type as the template parameter T. The function template has three parameters—the value searched for of type T, a pointer to the first array element, and the number of array ele- ments. The function template returns the index of the first element in the array that corresponds to the searched for value, or –1 if the value cannot be found in the array. Implement the function template. Use the technique described opposite as your algorithm for the interpolation search. Store the function tem- plate definition in the header file search.h. ■ Define a function template, insertionSort(), which sorts a numeric array in ascending order.The array elements are of the type of the tem- plate parameter T. The function template has two parameters—a pointer to the first array element, and the number of array elements.There is no return value. ■ Define a function template display() to display a numeric array on screen. The function template has two parameters—a pointer to the first array element and the number of array elements.There is no return value. ■ Use the function templates interpolSearch(), insertionSort(), and display() to define template functions for double and short types.To do so, define an array of double values and an array with short values. Write a main function that creates and calls each template function insertionSort() for the int and double types.Then display the sorted arrays. Add a call to each template function search() in your main function. Call search() passing values that exist and do not exist in the array. 740 ■ CHAPTER 32 TEMPLATES class FloatArr // Without conversion functions { private: float* arrPtr; // Dynamic member int max; // Maximum number, without having // to reallocate storage. int cnt; // Current number of elements void expand( int new Size); // Function to help // enlarge the array. public: FloatArr( int n = 256 ); FloatArr( int n, float val); FloatArr(const FloatArr& src); ~FloatArr(); FloatArr& operator=( const FloatArr& ); int length() const { return cnt; } float& operator[](int i) throw(BadIndex); float operator[](int i) const throw(BadIndex); void append( float val); void append( const FloatArr& v); FloatArr& operator+=( float val) { append( val); return *this; } FloatArr& operator+=( const FloatArr& v) { append(v); return *this; } void insert( float val, int pos) throw(BadIndex); void insert( const FloatArr& v, int pos ) throw(BadIndex); void remove(int pos) throw(BadIndex); friend ostream& operator<<( ostream& os, const FloatArr& v); }; Exercises The class FloatArr (as defined in Chap. 28, Ex. 1) EXERCISES ■ 741 Exercise 2 Define a class template Array<T, n> to represent an array with a maximum of n elements of type T.Attempting to address an array element with an invalid index should lead to an exception of the BadIndex (defined previously) error class being thrown. If there is no space left to insert an element in the array, an exception of the OutOfRange type should be thrown. ■ First define the error class OutOfRange without any data members. Use the error class BadIndex, which was defined in Exercise 1 of Chapter 28. ■ Change the existing FloatArr class into a class template, Array<T, n>. Use 255 as the default value for the parameter n of the class template. This allocates memory for the array statically. Now define a default con- structor and a constructor that initializes a given number of array ele- ments with a given value.You do not need to define a copy constructor, a destructor, or an assignment operator. As access methods define the size() and the length() methods, the size() method returns the maximum number of array elements, that is, n; the length() method returns the current number of elements in the array. Also define methods for inserting and deleting elements like those defined for the FloatArr class.The methods have a void return type and can throw exceptions of type BadIndex and/or OutOfRange. Additionally overload the index and shift operators <<.The subscript operator throws BadIndex type exceptions. ■ Test the class template Array<T,n> for double and int types first. Define arrays of the appropriate types, then insert and delete elements in the arrays. Output all the elements of the array. ■ Modify the test program by adding an array for objects of a class type. Use the DayTime class from Exercise 1, Chapter 19 for this purpose. Test the array template by defining an array with 5 DayTime class objects and inserting a few objects.Then display all the objects on screen. solutions 742 ■ CHAPTER 32 TEMPLATES ■ SOLUTIONS Exercise 1 // // interpol.cpp : Template function interpolSearch() // #include <iostream> using namespace std; template <class T> long interpolSearch(const T& key, T* vp, int len) { int expect, begin = 0, end = len - 1; double temp; if( end < 0 // Array is empty or || key > vp[end] // or key is out of || key < vp[begin] ) // range return -1; while( begin <= end ) { if(key > vp[end] || key < vp[begin] ) // Key is not return -1; // in range. temp = (double)(key - vp[begin]) / (vp[end]-vp[begin]); temp = temp * (end - begin) +0.5; expect = begin + (int)temp; if( vp[expect] == key ) // Key found? return expect; if( vp[expect] > key) end = expect - 1; else begin = expect+1; } return -1; } template <class T> void insertionSort( T* vp, int len) { T temp; for( int i=0; i < len; i++) { temp = vp[i]; // Take element out. int j; // Shift greater elements up: for( j = i-1; j >= 0 && vp[j] > temp; j ) vp[j+1] = vp[j]; vp[j+1] = temp; // Insert. } } SOLUTIONS ■ 743 template <class T> void display(T* vp, int len) { cout << "\n\nThe array: " << endl; for(int i = 0; i < len; i++) { cout << vp[i] << " "; if( (i+1)%10 == 0) cout << endl; } cout << endl; cin.get(); } // Two arrays for testing: short sv[5] = { 7, 9, 2, 4, 1}; double dv[5] = { 5.7, 3.5, 2.1, 9.4, 4.3 }; int main() { cout << "\nInstantiation for type short: " << endl; display(sv, 5); insertionSort(sv, 5); cout << "\nAfter sorting: "; display(sv, 5); short key; cout << "\nArray element? "; cin >> key; cin.sync(); int pos = interpolSearch(key, sv, 5); if( pos != -1) cout << "\nfound!" << endl, cin.get(); else cout << "\nnot found!" << endl, cin.get(); // cout << "\nInstantiation for type double: " << endl; display(dv, 5); insertionSort(dv, 5); cout << "\nAfter sorting: "; display(dv, 5); double dkey; cout << "\nArray element? "; cin >> dkey; cin.sync(); pos = interpolSearch(dkey, dv, 5); if( pos != -1) cout << "\nfound!" << endl, cin.get(); else cout << "\nnot found!" << endl, cin.get(); return 0; } 744 ■ CHAPTER 32 TEMPLATES Exercise 2 // // array.h // Use of class templates to represent arrays. // #ifndef _ARRAY_H_ #define _ARRAY_H_ #include <iostream> #include <iomanip> using namespace std; class BadIndex { private: int index; public: BadIndex(int i):index(i){} int getBadIndex() const { return index; } }; class OutOfRange { /* Without data members*/ }; template <class T, int n = 256> class Array { private: T arr[n]; // The array int cnt; // Current number of elements public: Array( ){ cnt = 0;} Array(int n, const T& val ); int length() const { return cnt; } int size() const { return n; } T& operator[](int i) throw(BadIndex) { if( i < 0 || i >= cnt ) throw BadIndex(i); return arr[i]; } const T& operator[](int i) const throw(BadIndex) { if( i < 0 || i >= cnt ) throw BadIndex(i); return arr[i]; } SOLUTIONS ■ 745 Array& operator+=( float val) throw(OutOfRange) { append( val); return *this; } Array& operator+=(const Array& v) throw(OutOfRange) { append(v); return *this; } void append( T val) throw(OutOfRange); void append( const Array& v) throw(OutOfRange); void insert( T val, int pos) throw(BadIndex, OutOfRange); void insert( const Array& v, int pos ) throw(BadIndex, OutOfRange); void remove(int pos) throw(BadIndex); }; template <class T, int n > Array<T,n>::Array(int m, const T& val ) { cnt = m; for(int i=0; i < cnt; i++ ) arr[i] = val; } template <class T, int n > void Array<T,n>::append( T val) throw(OutOfRange) { if( cnt < n) arr[cnt++] = val; else throw OutOfRange(); } template <class T, int n > void Array<T,n>::append( const Array<T,n>& v) throw(OutOfRange) { if( cnt + v.cnt > n) // Not enough space. throw OutOfRange(); int count = v.cnt; // Necessary if // v == *this for( int i=0; i < count; ++i) arr[cnt++] = v.arr[i]; } 746 ■ CHAPTER 32 TEMPLATES template <class T, int n > void Array<T,n>::insert( T val, int pos) throw(BadIndex, OutOfRange) { insert( Array<T,n>(1,val), pos); } template <class T, int n > void Array<T,n>::insert( const Array<T,n>& v, int pos ) throw(BadIndex, OutOfRange) { if( pos < 0 || pos >= cnt) throw BadIndex(); // Invalid position. if( n < cnt + v.cnt) throw OutOfRange(); int i; for( i = cnt-1; i >= pos; i) // Shift up arr[i+v.cnt] = arr[i]; // starting at pos. for( i = 0; i < v.cnt; ++i) // Fill the gap. arr[i+pos] = v.arr[i]; cnt = cnt + v.cnt; } template <class T, int n > void Array<T,n>::remove(int pos) throw(BadIndex) { if( pos >= 0 && pos < cnt) { for( int i = pos; i < cnt-1; ++i) arr[i] = arr[i+1]; cnt; } else throw BadIndex(pos); } template <class T, int n > ostream& operator<<(ostream& os, const Array<T,n>& v) { int w = os.width(); // Save the field width for( int i = 0; i < v.cnt; ++i) { os.width(w); os << v.arr[i]; } os << endl; return os; } #endif SOLUTIONS ■ 747 // // DayTime.h // Class DayTime with relational operators, // the operators ++ and (prefix and postfix), // and the operators << and >> for I/O. // // The same as in Chapter 19. // // Array_t.cpp // Testing class templates Array<T,n>. // #include "array.h" #include "DayTime.h" #include <cstdlib> #include <iostream> #include <iomanip> using namespace std; typedef Array<int, 100> IntArr; typedef Array<double> DoubleArr; typedef Array<DayTime, 5> DayTimeArr; int main() { try { const DoubleArr vd(10, 9.9); DoubleArr kd; cout << "\nThis is the constant array of doubles: \n"; cout << setw(8) << vd; kd = vd; cout << "\nAn array of doubles after the assignment: " << endl; cout << setw(8) << kd; kd.remove(3); // Delete the element at // position 3. kd.append(10.0); // Add a new element. kd.append(20.0); // And repeat! cout << "\nThis is the modified array: " << endl; cout << setw(8) << kd; 748 ■ CHAPTER 32 TEMPLATES IntArr vi; int i; for(i=0; i < 10; i++) vi.append(rand()/100); cout << "\nThis is the array of int values: \n"; cout << setw(12) << vi; vi += vi; cout << "\nAnd append: \n"; cout << setw(12) << vi; IntArr ki(vi); cout << "\nThis is the copy of the array: \n"; cout << setw(12) << ki; DayTimeArr vt; // Array of DayTime objects. DayTime temp; for(i=0; i < 3; i++) { if( !(cin >> temp)) break; vt.append(temp); } cout << "\nThe array with objects of type DayTime:\n"; for(i=0; i < 3; i++) cout << setw(20) << vt[i] << endl; } catch(BadIndex& err) { cerr << "\nIndex " << err.getBadIndex() << " invalid"; exit(1); } catch(OutOfRange& ) { cerr << "\nArray is full!"; exit(2); } return 0; } . help // enlarge the array. public: FloatArr( int n = 256 ); FloatArr( int n, float val); FloatArr(const FloatArr& src); ~FloatArr(); FloatArr& operator=( const FloatArr& ); int length(). } float& operator[](int i) throw(BadIndex); float operator[](int i) const throw(BadIndex); void append( float val); void append( const FloatArr& v); FloatArr& operator+=( float val) { append(. existing FloatArr class into a class template, Array<T, n>. Use 255 as the default value for the parameter n of the class template. This allocates memory for the array statically. Now define

Ngày đăng: 06/07/2014, 17:21

TỪ KHÓA LIÊN QUAN