270 likes | 421 Views
159.234 LECTURE 17. 20. More on Templates. An abstract recipe for producing concrete code. Templates. 19. Some Terms. Function Template. A function template is a template used to generate functions. e.g. template <class T> T Max (T x, T y) { if (x > y) return x; else return y;
E N D
159.234LECTURE 17 20 More on Templates An abstract recipe for producing concrete code.
Templates 19 Some Terms Function Template A function template is a template used to generate functions. e.g. template <class T> T Max(T x, T y) { if (x > y) return x; else return y; } Template Function A template function is a function that is produced by a template. e.g. This function call tells the compiler to generate the actual template function. i = Max(j,k);
Templates 19 Some Terms Class Template A class template is a template that is used to generate classes. e.g. template <class T> class Vector{ //class interface }; Template Class A template class is a class that is produced by a template. Actual template class e.g. Vector<int> m(100); Vector<Date> d(200);
Templates 19 Friends A friend function that does not use a template specification is universally a friend of all instantiations of the template class. template <class T> class matrix{ public: friend void foo_bar(); //universal friend vect<T> product(vect<T> v); //instantiated }; A friend function that incorporates template arguments is specifically a friend of its instantiated class.
Templates 19 Static Members Static members are not universal but are specific to each instantiation. template <class T> class Vect{ public: static int count; //… }; Vect<int> a; Vect<double> b; Static variables Vect<int>::count and Vect<double>::count are distinct.
Templates 19 Default Template Arguments You can assign a default type to your class template Default type template <class T=int> class Vect{ public: //… }; Instantiation: Vect< > a; Vect<double> b;
Templates 19 Member Templates Members may themselves be templates inside the template class. template <class T1> class Vect{ public: template<class T2> class Complex{ //… //can use T1 and T2 in Complex }; //can only use T1 in Vect }; Vect<int>::Complex<float> a; class member template New feature of ANSI standard - yet to be implemented on most C++ compilers
Common Errors with Templates 1. Not using template<class T> when defining member function for class templates. 2. Not using the generic type for parameters/variables. 3. Not placing class, before every formal type parameter. Correct: template<class T, class S> If a template is invoked with a user defined class type and that template uses operators (==, +, <=, etc.) with objects of that class type, then those operators must be overloaded.
Templates vs. Macros Macros present the possibility of having side effects because they do not usually have type checking. #define SQ(A) ((A)*(A)) template<class T> T square (T x){ return x*x; }
Templates vs. Macros #define SQ(A) ((A)*(A)) template<class T> T square (T x){ return x*x; } • int main(){ • int a = 7; • cout<<square(a++)<<endl; • cout<<"and a is "<<a<<endl; • cout <<SQ(a++)<<endl; • cout<<"and a is "<<a<<endl; • } • /*output: • 49 • and a is 8 • 64 • and a is 10 • */
Templates 19 Class Template Example x Vector Class Template size data Vector() Vector() ~Vector() operator=() operator[] Size() Vector <short> public: Vector() Vector() ~Vector() operator=() operator[] Size() y size data copy() protected: copy() Instantiated from the Class template x & y are both instantiated from the Template class Vector<short> Cannot be invoked by any of the class instances See VectorT.cpp
Templates 19 SubClass Template Example What if we want to allow the user to designate the range of indexes for the Vector class? Vector Class Template Vector() Vector() ~Vector() operator=() operator[] Size() public: e.g. Instead of the range [0, 100], we want to have [1, 100], or even [-100, 100]. protected: copy() We can derive a new class that could Inherit all the functionalities of Vector, as well as perform some modifications.
Nested Templates 19 Passing Template Classes to Template Parameters Array class template connects to the Vector class template via inheritance. Array Class Template template <class T> class Array : public Vector<T>{ public: Array(inti, int j) : Vector<T>(j-i+1), i0(i) {} Array(const Array<T>& v) : i0(v.i0), Vector<T>(v) {} T& operator[](inti) const { return Vector<T>::operator[](i-i0);} intfirstsubscript() const {return i0;} intlastsubscript() const {return i0 + Vector<T>::size - 1;} protected: int i0; //index 0 (or first index number) }; Explicitly calls the Vector operator[] See Subclass Template for Vectors.cpp
Templates 19 Class Template Example What if we want to allow for an ordinary array to be replicated as a vector? int a[] = {11, 22, 33, 44, 55}; Vector<int> v(a); See Replicating an ordinary array as a vector.cpp
// multidimensional_arrays.cpp // compile with: /EHsc // arguments: 3 #include <limits> // Includes DBL_MAX #include <iostream> const int cMkts = 4, cFacts = 2; // Declare a float that represents the transportation costs double TransportCosts[][cMkts] = { { 32.19, 47.29, 31.99, 19.11 }, { 11.29, 22.49, 33.47, 17.29 }, { 41.97, 22.09, 9.76, 22.55 } }; // Calculate size of unspecified dimension const int cFactories = sizeof TransportCosts / sizeof( double[cMkts] ); http://msdn.microsoft.com/en-us/library/7wkxxx2e.aspx
Nested Templates 19 Passing Template Classes to Template Parameters Our own class templates can accept built-in classes as template parameter: Vector<string> a; Since template classes work like ordinary classes, we can also pass them to template parameters: Stack<Vector<int>> b; Array<Stack<Vector<int>> > c; See Matrix.cpp
Nested Templates 19 Passing Template Classes to Template Parameters Matrix – essentially a 2D vector a 2-by-3 Matrix is a table with 2-rows & 3-columns It can be represented as a 2-element Vector, each of whose elements is a 3-element Vector: This representation would allow us to use our Vector class template to define a new Matrix class template. See Matrix.cpp
Nested Templates 19 Passing Template Classes to Template Parameters To facilitate dynamic allocation of memory, we define a Matrix as a Vector of Pointers to Vectors Vector< Vector<T>* > When the Matrix class template is instantiated, the Instances of the resulting class will contain vectors of pointers to vectors. See Matrix.cpp
Nested Templates 19 Passing Template Classes to Template Parameters Matrix class template connects to the Vector class template via composition. Matrix Class Template template<class T> class Matrix{ public: Matrix(unsigned r=1, unsigned c=1) : row(r) {//… } ~Matrix(){ //… } Vector<T>& operator[](unsigned i) const {//… } unsigned rows() {return row.size(); } unsigned columns() {return row[0]->size(); } //(*row).size() protected: Vector<Vector<T>*> row; }; Vector of pointers to Vectors See Matrix.cpp
Nested Templates 19 Passing Template Classes to Template Parameters Matrix Class Template : Constructor Matrix(unsigned r=1, unsigned c=1) : row(r) { for(int i=0; i < r; i++) { row[i] = new Vector<T>(c); } } See Matrix.cpp
Nested Templates 19 Passing Template Classes to Template Parameters Matrix Class Template : Destructor ~Matrix(){ for(int i=0; i < row.Size(); i++) { delete row[i]; } } See Matrix.cpp
Nested Templates 19 Passing Template Classes to Template Parameters Matrix Class Template : Subscripting Operator Vector<T>& operator[](unsigned i) const { return *row[i]; } unsigned rows() {return row.Size(); } unsigned columns() {return row[0]->Size(); } //(*row).size() See Matrix.cpp
Nested Templates 19 Passing Template Classes to Template Parameters Creating an Instance of the Matrix Class Template : Matrix<float> a(2, 3); a Matrix() ~Matrix() operator[] rows() columns() row data data size=2 size=3 size=3 0 0 0 0.0 1.0 1 1 1 0.1 1.1 2 2 0.2 1.2 Matrix<float> Vector<float> Vector<float> Vector of pointers to Vectors Matrix<float> See Matrix.cpp
Nested Templates 19 Extracting an element of the Matrix Template Class a: a[1][2] invokes the following operators: Matrix operator[1] Vector operator[1] Vector operator[2] Matrix operator[1] Vector operator[1] data[i] = 0x4d3f58 Vector operator[2] data[i] = 1.2 m[1][2] = 1.2 a Matrix() ~Matrix() operator[] rows() columns() row data data size=2 size=3 size=3 0 0 0 0.0 1.0 1 1 1 0.1 1.1 2 2 0.2 1.2 Matrix<float> Vector<float> Vector<float> Matrix<float> See Matrix.cpp
Nested Templates 19 Extracting an element of the Matrix Template Class a: Matrix operator[0] Vector operator[0] Vector operator[2] a[0][2] invokes the following operators: a Matrix() ~Matrix() operator[] rows() columns() row data data size=2 size=3 size=3 0 0 0 0.0 1.0 1 1 1 0.1 1.1 2 2 0.2 1.2 Matrix<float> Vector<float> Vector<float> Matrix<float> See Matrix.cpp, Matrix_stl.cpp
Summary C++ uses templates to provide generic programming. Templates are one of C++’s features that allow for software reuse. By allowing the user of the class template to provide the data type through the specification of the type parameter during instantiation, the same code can be utilized for different types.
Standard Template Library (STL) A large collection of reusable components. The key components of the STL --containers are data structures created using templates. A container is an object that contain objects. Using STL can save considerable time and effort, and result in higher quality programs.