Class的成员也可以是templates:既可以是nested class templates,也可以是member function templates。
我们还是使用Stack<T>这个例子:
通常只有当两个 stacks 类型相同,也就是当两个stacks 拥有相同类型的元素时,你才能对它们相互赋值(assign),也就是将某个 stack 整体赋值给另一个。你不能把某种类型的 stack赋值给另一种类型的stack,即使这两种类型之间可以隐式转型:
Stack<int> intStack1, intStack2; // stacks for ints
Stack<float> floatStack; // stack for floats
...
intStack1 = intStack2; // OK:两个 stacks 拥有相同类型
floatStack = intStack1; // ERROR:两个 stacks 类型不同
为了实现隐式转换功能,现在:
// basics/stack5decl.cpp
template <typename T>
class Stack {
private:
std::deque<T> elems; // 元素
public:
void push(T const&); // push 元素
void pop(); // pop 元素
T top() const; // 传回 stack 顶端元素
bool empty() const { // stack 是否为空
return elems.empty();
}
// 以「元素类型为 T2」的 stack做为赋值运算的右手端。
template <typename T2>
Stack<T>& operator= (Stack<T2> const&);
};
新增加的 assignment 运算符的具体实现如下:
template <typename T>
template <typename T2>//重点
Stack<T>& Stack<T>::operator= (Stack<T2> const& op2)
{
if ((void*)this == (void*)&op2) { // 判断是否赋值给自己
return *this;
}
Stack<T2> tmp(op2); // 建立 op2的一份拷贝
elems.clear(); // 移除所有现有元素
while (!tmp.empty()) { // 复制所有元素
elems.push_front(tmp.top());
tmp.pop();
}
return *this;
}
注意,前述的 template assignment 运算符并不取代 default assignment 运算符。如果你在相同 类型的 stack 之间赋值,编译器还是会采用 default assignment 运算符。