Clo*_*ees 6 c++ templates llvm-clang
我试图使用clang 3.3在我的Mac上为经典的复制和交换习惯编译以下代码
template<typename T> class node{
private:
node<T>* left;
node<T>* right;
T value;
public:
friend void swap(node<T>&, node<T>&);
// other stuff
}
Run Code Online (Sandbox Code Playgroud)
然而链接器抱怨道.我现在明白我应该将该函数声明为模板.但是,如果我遵循建议的风格,将出现的错误这里从MSDN:
template <class T> class Array {
T* array;
int size;
public:template<class T>
//...
template <class T>
friend Array<T>* combine(Array<T>& a1, Array<T>& a2);
};
Run Code Online (Sandbox Code Playgroud)
我做了复制粘贴,但得到以下错误:
te.cpp:33:19: error: declaration of 'T' shadows template parameter
template<class T>
^
te.cpp:4:17: note: template parameter is declared here
template <class T> class Array {
^
1 error generated.
Run Code Online (Sandbox Code Playgroud)
这是一个铿锵的bug吗?MSDN网站建议它在VC++下运行.
PS:我知道有两种解决方案:在Stackoverflow文章中定义模板类中的friend函数,或者在模板类中以下列方式声明:
template <typename U> friend void swap(node<U>&, node<U>&);
Run Code Online (Sandbox Code Playgroud)
但是都困扰我.第一个集群的类声明,而第二个集合友谊交换采用不同的类型.
更新:第三种解决方案是使用具有专业化的前向声明:
template <typename T> class node;
template <typename T> void swap (node<T>&, node<T>&);
template <typename T> class node{
//...
friend void swap<> (node<T>&, node<T>&);
};
Run Code Online (Sandbox Code Playgroud)
这也适用于铿锵声.
我相信这就是您想要的(恰好是您刚刚添加到问题中的第三个选项)
#include <utility>
template <typename T> class node;
template <typename T> void swap(node<T> & a, node<T> & b);
template<typename T> class node {
private:
node<T>* left;
node<T>* right;
T value;
public:
friend void swap<>(node<T>&, node<T>&);
};
template <typename T> void swap(node<T> & a, node<T> & b) {
std::swap(a.left, b.left);
std::swap(a.right, b.right);
std::swap(a.value, b.value);
}
int main() {
node<int> x, y;
swap(x, y);
}
Run Code Online (Sandbox Code Playgroud)