C ++ Primer study note _ 79 _ templates and generic programming

Source: Internet
Author: User
Tags export class

Template and generic programming-template compilation Model

Introduction:

When the compiler sees the template definition, it does not generate code immediately. The compiler generatesTemplate instances of specific types.

Generally, when calling a function [not a template], the compiler only needs to see the declaration of the function. Similarly, when defining objects of the class type, the class definition must be available,The definition of a member function is not mandatory.. Therefore, the class definition and function declaration should be placed in the header file, while the definition of common functions and class member functions should be placed in the source file.

The template is different: To be instantiated, the compiler must be able to accessSource code of the template Definition. When calling a function template or a member function of a class template, the compiler must define the function,Code that is usually put in the source file.

The standard C ++ defines two models for the compilation template code. In the two models, the method for constructing a program is largely the same:Class Definition and function declaration are placed in the header file, AndPut the function definition and member definition in the source file.. The difference between the two models is how the compiler uses definitions from source files. As described in this book, all compilers support the first model toInclude"Model, only some compilers support the second model,"Separate Compilation"Model.



1. Include the compilation Model

InInclude compilation Model, CompilerMust seeThe definitions of all templates used. Generally, you can add a # include Directive to the header file of the declared function template or class template to make the definition available. This # include introduces the source file containing the definition:

//in utilities.h#ifndef UTILITIES_H_INCLUDED#define UTILITIES_H_INCLUDED#include "utilities.cpp"template <class T>int compare(const T &,const T &);#endif // UTILITIES_H_INCLUDED

//in  utilities.cpp#include "utilities.h"template <class T>int compare(const T &val1,const T &val2){    if (val1 < val2)        return -1;    if (val2 < val1)        return 1;    return 0;}

This policy allows us to keep the header file and implement file separation, but we need to ensureThe compiler can see two types of files when using the template code..

Some compilers that use models, especially older compilers, can generate multiple instances. If two or more independently compiled source files use the same template, these compilers willGenerate an instance for the template in each file. Generally, this method meansThe given template will be instantiated more than once. InLinkInPre-LinkStage, CompilerWill select an instantiation and discard other. In this case, if there are many files that instantiate the same template, the compilation performance will be significantly reduced. For many applications, this performance reduction during compilation is unlikely to become a problem on modern computers. However,In a large system environment,Selection during compilation may become very important.

This compiler usually supports some mechanisms to avoid the implicit compilation overhead in multiple instantiations of the same template. The compiler optimizes the compilation performance in different ways. If the Compilation Time of the program using the template is difficult to bear, please refer to the compiler user guide to see what support your compiler can provideAvoid unnecessary instantiation.



2. Compile models separately

InCompile models separately, The compiler willTrace-related template Definitions. However, the compiler must be aware of the given template definition.ExportKeywordsTo do this.

Export keyword can be specifiedThe given definition may need to be instantiated in other files.. In a program,A template can only be definedExportOnce. The compiler determines how to locate the template definition when these instantiation is required. The export keyword does not need to appear in the template declaration.

Generally, we specify the function template as exported in the function template definition, which is achieved by including the export keyword before the keyword template:

//in  utilities.hexport template <typename Type>int compare(const Type &val1,const Type &val2)/***/

The declaration of this function template should be put in the header file as usual, and the declaration does not need to specify the export.



It is more complicated to use export for class templates. Generally,Class Declaration must be placed in the header fileIn the header file, the class definition body should not use the keyword export. If export is used in the header file,The header file can only be used by one source file in the program..

Instead, use export in the class implementation file:

// in header file template <class Type> class Queue { ... }; 

// in implementation fileexport template <class Type> class Queue; #include "Queue.h" //...

The export class members are automatically declared as exported. You can also setThe individual members of the class template are declared as exportedIn this case, the keywordExportNot specified by the class template itself, But only in the exportedSpecified on a specific member Definition.The definition of the exported member function is not visible when the member function is used.. The definition of any non-exported member must be treated as in the inclusion Model: The definition should be placed in the header file of the definition class template.

// P544 exercise 16.27 // in middle. h # ifndef MIDDLE_H_INCLUDED # define MIDDLE_H_INCLUDED # include <vector> # include <algorithm> using namespace std; template <typename Type> bool middle (const vector <Type> &, Type &); # include "middle. cpp "# endif // MIDDLE_H_INCLUDED

//in middle.cpp#include "middle.h"template <typename Type>bool middle(const vector<Type> &vec,Type &val){    vector<Type> tmp(vec);    sort(tmp.begin(),tmp.end());    if (tmp.size() % 2 == 0)    {        return false;    }    typename vector<Type>::iterator index =        tmp.begin() + tmp.size()/2;    if (*index > *(index -1) && *(index) < *(index + 1))    {        val = *index;        return true;    }    return false;}

// In main. cpp # include <iostream> # include "middle. h "using namespace std; int main () {int ia [] = {1, 2, 4, 5, 6, 7}; int ai [] = {1, 2, 3, 4, 5, 6 }; vector <int> ivec1 (ia, ia + 7), ivec2 (ai, ai + 6); int val; if (middle (ivec1, val )) {cout <"Middle:" <val <endl;} else {cout <"No Middle! "<Endl;} if (middle (ivec2, val) {cout <" Middle: "<val <endl;} else {cout <" No Middle! "<Endl ;}/ ** Note: The g ++ compiler supports model inclusion *, but cannot include template implementation files into the project. * Otherwise, compilation errors may occur! */

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.