1. 在类模板中使用类型时要加上模板类型,如:Stack<T>。而表示类时就只用类名,如:Stack。
2. 一个绝对异常安全并且返回被删除元素的pop()是不可能的。参考[CargillExceptionSafty]
3. 对于类模板,成员函数只有在被使用的时候才会被实例化。如果类模板中含有静态成员,那么用来实例化的每种类型,都会实例化这些静态成员。
4. 特化类模板
template<>
class Stack<std::string>
{
public:
void push(std::string const& elem);
void pop();
std::string top() const;
bool empty() const;
private:
//Stack(Stack<T> const&);
Stack<std::string>& operator=(Stack<std::string> const&);
private:
std::vector<std::string> m_elems;
};
void Stack<std::string>::push(const std::string &elem)
{
m_elems.push_back(elem);
}
5. 局部特化
template <typename T1, typename T2>
class MyClass {
...
};
可以局部特例化为以下几种类型:
template <typename T>
class MyClass<T,T> {
...
};
template <typename T>
class MyClass<T,int> {
...
};
template <typename T1, typename T2>
class MyClass<T1*,T2*> {
...
};
同等匹配问题:
比如:
Myclass<int,int> m; //equally suitable to MyClass<T,T> and MyClass<T,int>
MyClass<int*,int*> m; //equally suitable to MyClass<T,T> and MyClass<T1*,T2*>
解决上述二义性的方法就是提供一个完全匹配的类型的特化,比如提供一个相同类型的指针的特化:
template <typename T>
class MyClass<T*,T*> {
...
};
6. 缺省模板参数
下面的例子就将CONT的默认值设置为std::vector<T>
template<typename T, typename CONT = std::vector<T> >
class Stack {
private:
CONT elems;
};
7. 非类型的类模板参数
template<typename T, int MAXSIZE>
class Stack {
private:
T elems[MAXSIZE];
...
};
非类型模板参数的限制:通常它们可以是常整数(包括枚举值)或者指向外部链接对象的指针。
浮点数和类对象是不允许作为非类型模板参数的
template <char const* name>
class MyClass {
…
};
MyClass<"hello"> x; // ERROR: string literal "hello" not allowed
//You cannot use a global pointer either:
template <char const* name>
class MyClass {
…
};
char const* s = "hello";
MyClass<s> x; // ERROR: s is pointer to object with internal linkage
//However, the following is possible:
template <char const* name>
class MyClass {
…
};
extern char const s[] = "hello";
MyClass<s> x; // OK