模板提供了代码复用。在使用模板时首先要实例化,即生成一个具体的函数或类。函数模板的实例化是隐式实现的,即由编译系统根据对具体模板函数(实例化后的函数)的调用来进行相应的实例化,而类模板的实例化是显式进行的,在创建对象时由程序指定。
一个模板有很多实例,是否实例化模板的某个实例由使用点来决定,如果未使用到一个模板的某个实例,则编译系统不会生成相应实例的代码。
在C++中,由于模块是分别编译的,如果在模块A中要使用模块B中定义的一个模板的某个实例,而在模块B中未使用这个实例,则模块A无法使用这个实例,除非在模块A中也定义了相应的模板。因此模板是基于源代码复用,而不是目标代码复用。
例:
// file1.h
template <class T>
class S
{ T a;
public:
void f();
};
// file1.cpp
#include "file1.h"
template <class T>
void S<T>::f()
{ …
}
template <class T>
T max(T x, T y)
{ return x>y?x:y;
}
void main()
{ int a,b;
float m,n;
max(a,b);
max(m,n);
S<int> x;
x.f();
}
// file2.cpp
#include "file1.h"
extern double max(double,double);
void sub()
{ max(1.1,2.2); //Error,no appropriate instance
S<float> x;
x.f(); //Error, corresponding instance has no appropriate implementation
}
一个模板有很多实例,是否实例化模板的某个实例由使用点来决定,如果未使用到一个模板的某个实例,则编译系统不会生成相应实例的代码。
在C++中,由于模块是分别编译的,如果在模块A中要使用模块B中定义的一个模板的某个实例,而在模块B中未使用这个实例,则模块A无法使用这个实例,除非在模块A中也定义了相应的模板。因此模板是基于源代码复用,而不是目标代码复用。
例:
// file1.h
template <class T>
class S
{ T a;
public:
void f();
};
// file1.cpp
#include "file1.h"
template <class T>
void S<T>::f()
{ …
}
template <class T>
T max(T x, T y)
{ return x>y?x:y;
}
void main()
{ int a,b;
float m,n;
max(a,b);
max(m,n);
S<int> x;
x.f();
}
// file2.cpp
#include "file1.h"
extern double max(double,double);
void sub()
{ max(1.1,2.2); //Error,no appropriate instance
S<float> x;
x.f(); //Error, corresponding instance has no appropriate implementation
}