with c templates
play

with C++ Templates Templates Thomas Gschwind <thg at zurich dot - PowerPoint PPT Presentation

Advanced Software Engineering with C++ Templates Templates Thomas Gschwind <thg at zurich dot ibm dot com> Templates Polymorphisms Specialization Declaration and Use Classes and Members Ambiguities An Example


  1. Advanced Software Engineering with C++ Templates Templates Thomas Gschwind <thg at zurich dot ibm dot com>

  2. Templates  Polymorphisms  Specialization  Declaration and Use  Classes and Members  Ambiguities  An Example (pvector) Th. Gschwind. Advanced Software Engineering with C++ Templates. 83

  3. Types of Polymorphisms  “Ad - hoc” • Overloading • Statically resolved by the compiler (using argument types)  Dynamic • Using virtual member functions • Method to be invoked identified during run-time (using the virtual method table)  Static or Parametric • Using templates • Function to be invoked identified statically • Concrete Functions/Classes are generated for the individual parameter types Th. Gschwind. Advanced Software Engineering with C++ Templates. 84

  4. Templates – Why?  Writing gcm, lcm, and swap for all kinds of types is tedious  We want to define the function once and use it for all types possible • Sort of like Lisp, Smalltalk, Python, Ruby, you name it… • Just more efficiently Th. Gschwind. Advanced Software Engineering with C++ Templates. 85

  5. Templates: Declaration and Definition  Allow the use of the same function/class for different types  The types become new compile-time parameters • Types need to implement the routines used by the template  The definition must be available to the compiler  Are checked and resolved statically (during compile time) • Function calls can be resolved during compilation time  Support generic programming • Many functions are the same independently of the data type This is “ old style ”, one should use typename template<class T> instead but some people still prefer class. inline T min(T a, T b) { If you use an antiquated C++ compiler you may return a<b ? a : b; have to use class. } Th. Gschwind. Advanced Software Engineering with C++ Templates. 86

  6. Templates: Use  Are invoked like any other function (mostly) template < typename T> inline T min(T a, T b) { return a<b?a:b; } const double pi=3.141596; void f() { min(2.718282, 1.0); min('a', 'z'); min(1, 26); min(pi, 2.718282); min('a', 26); min(2.718282, 1); } Th. Gschwind. Advanced Software Engineering with C++ Templates. 89

  7. Templates: Use template < typename T> template < typename T> inline T min(T a, T b) { inline T min(T a, T b) { return a<b?a:b; return a<b?a:b; } } const double pi=3.141596; const double pi=3.141596; void f() { void f() { min(2.718282, 1.0); min(2.718282, 1.0); // ok min('a', 'z'); min('a', 'z'); // ok min(1, 26); min(1, 26); // ok min(pi, 2.718282); min(pi, 2.718282); // ok min('a', 26); min('a', 26); // error, ambiguous min(2.718282, 1); min(2.718282, 1); // error, ambiguous } }  Template parameters must be unambiguously resolved  Otherwise, the ambiguity needs to be resolved manually Th. Gschwind. Advanced Software Engineering with C++ Templates. 90

  8. Templates: Resolving Ambiguities  Unlike for “normal” functions, there is no implicit conversion for templates  Explicit • If necessary min<int>('a', 26); • Or even if unnecessary min<const double>(pi, 2.718282); Th. Gschwind. Advanced Software Engineering with C++ Templates. 92

  9. Mixing Templates and Non-Templates  Templates and non-templates can be mixed  Can define a template-based function min  And define a non template-based function min at the same time  Non-templates are preferred over templates if no type conversion necessary template < class T> inline T min(T a, T b) { return a<b ? a : b; } inline double min(double a, double b) { return a<b ? a : b; } Th. Gschwind. Advanced Software Engineering with C++ Templates. 93

  10. Templates: Resolving Ambiguities (cont‘d)  We can create separate helper functions • Helper functions may be based on the underlying template inline int min( int x, int y) { return min< int >(x,y); } inline double min( double x, double y) { return min< double >(x,y); }  This approach not only looks tedious but is also error- prone, clumsy, … Th. Gschwind. Advanced Software Engineering with C++ Templates. 94

  11. min Template – A Problem?  We have seen it works fine with numbers and characters  What about C-style strings? cout << min("Hello", "World") << endl;  The above will compare the addresses where the strings are stored • It will return the string with the smaller address  This is not what the typical developer wants …  For strings it would be better to use a lexicographical comparison such as strcmp … Th. Gschwind. Advanced Software Engineering with C++ Templates. 95

  12. Specialization ( 1 st Attempt )  Templates and non-templates can be mixed  Define a non template-based function min for C strings template < typename T> inline T min(T a, T b) { return a<b ? a : b; } inline char *min( char *a, char *b) { return strcmp(a,b)<0 ? a : b; } inline const char *min( const char *a, const char *b) { return strcmp(a,b)<0 ? a : b; } #include "min.h" void foo(char *x, char *y, const char *z) { cout << min(x,y) << endl; // yes cout << min(x,z) << endl; // yes cout << min<const char*>(x,z) << endl; // compiles but wrong } We are asking for the template, so we get the template … Th. Gschwind. Advanced Software Engineering with C++ Templates. 96

  13. Template Specialization ( 2 nd and Final Attempt )  C++ allows us to specialize an existing template for specific types template < typename T> inline T min(T a, T b) { return a<b ? a : b; } template<> inline char *min<char *>(char *a, char *b) { return strcmp(a,b)<0 ? a : b; } template<> inline char *min<const char *>(const char *a, const char *b) { return strcmp(a,b)<0 ? a : b; } Compiler error; as we discussed, there is no #include "min.h" implicit parameter void foo(char *x, char *y, const char *z) { conversions for templates. cout << min(x,y) << endl; // yes cout << min(x,z) << endl; // error cout << min<const char*>(x,z) << endl; // yes } Th. Gschwind. Advanced Software Engineering with C++ Templates. 97

  14. Templates: Classes and Members  Works exactly the same  Simply put template <typename T, typename U, …> in front of the declaration  It is even OK, to introduce new template parameters for individual member functions Th. Gschwind. Advanced Software Engineering with C++ Templates. 98

  15. A Persistent pvector Class  We want to implement a persistent version of C++’s vector class  Reads all elements from a file in the constructor  Writes all elements back to the file in the destructor template < typename T> class pvector { string filename; vector<T> v; … public : pvector(string fname) : filename(fname) { readvector(); } ~pvector() { writevector(); } void push_back( const T &el) { v.push_back(el); } void pop_back() { v.pop_back(); } … Th. Gschwind. Advanced Software Engineering with C++ Templates. 99

  16. A Persistent pvector Class (cont’d) template < typename T> class pvector { string filename; vector<T> v; void readvector() { ifstream ifs(filename); for (;;) { T x; ifs >> x; if(!ifs.good()) break; v.push_back(x); } } void writevector() { ofstream ofs(filename); typename vector<T>::iterator fst=v.begin(), lst=v.end(); while (fst!=lst) ofs << *fst++ << endl; } OR starting with C++11, simply: for ( const T &elem : v) ofs << elem << endl; … Th. Gschwind. Advanced Software Engineering with C++ Templates. 100

  17. A Persistent pvector Class (cont’d)  What happens if we pass the pvector around? void foo(pvector< int > pv) { if (pv.size()>0) cout << pv[0] << endl; pv.push_back(17); } int main( int argc, char *argv[]) { pvector< int > pv("/tmp/pvector-int.txt"); foo(pv); }  Hence, maybe we want to disable the copy-constructor for pvector<T> Th. Gschwind. Advanced Software Engineering with C++ Templates. 101

  18. Advanced Software Engineering with C++ Templates Separate Compilation Thomas Gschwind <thg at zurich dot ibm dot com>

  19. Separate Compilation  C++ versus Java  Variables  Routines (Functions & Operators)  Types (Structures, Classes)  Makefiles Th. Gschwind. Advanced Software Engineering with C++ Templates. 103

  20. Separate Compilation  Why? • Having only one source file is unrealistic • Break the code up into its logical structure • Reduction of compile time • Only changed parts need to be recompiled  How? • Use multiple source files • Need to know what information about functions and variables “used” from other files Th. Gschwind. Advanced Software Engineering with C++ Templates. 104

  21. Separate Compilation in Java  Each Java file is compiled into a class file  If a Java class invokes a method of another class, the compiler consults that other class file to • Determine whether the class provides the requested method • Determine whether a class file implements a given interface • etc. • Hence, the .class file contains the entire interface  That’s why in Java, the compiler needs the class path  Finally, all class files are loaded by the Java Virtual Machine (and “linked”)  Java source code can be reconstructed from .class file (see Java Decompiler: jd, jad) Th. Gschwind. Advanced Software Engineering with C++ Templates. 105

Recommend


More recommend