正确的朋友模板函数语法
Correct syntax for friend template function
在C 编程语言中,第四版 - 第23.4.7章朋友,我找到了以下示例(我对其进行了稍作修改以显示相关部分):
template<typename T>
class Vector {
public:
friend Vector operator*<>(const Vector& v, int f);
^^ ~~~~ ?
};
template<typename T>
Vector<T> operator*(const Vector<T>& v, int f) {
return v;
}
我尝试编译它,但是我会得到以下错误(clang):
main.cpp:8:20: error: friends can only be classes or functions
friend Vector operator*<>(const Vector& v, int f);
^
main.cpp:8:29: error: expected ';' at end of declaration list
friend Vector operator*<>(const Vector& v, int f);
^
;
2 errors generated.
书籍解释:
&lt;>需要在朋友函数的名称之后清楚地表明朋友是模板函数。如果没有&lt;>,将假设一个非模板函数。
就是这样。
没有<>
,此代码编译,但是当使用操作员*时(例如: Vector<int> v; v*12;
),则会出现链接器错误:
main.cpp:(.text+0xb): undefined reference to `operator*(Vector<int> const&, int)'
因此,我认为需要<>
告诉编译器,每次为给定类型实例化矢量模板应生成操作员*的功能模板。
但是我在书中的示例中做错了什么,为什么?
正如书所说的,
需要
<>
在需要朋友函数的名称之后清楚地表明朋友是模板函数。
这意味着,名称应参考函数模板,该函数模板应提前声明(作为模板)。例如
// forward declaration of the class template
template<typename T>
class Vector;
// declaration of the function template
template<typename T>
Vector<T> operator*(const Vector<T>& v, int f);
template<typename T>
class Vector {
public:
// friend declaration
friend Vector operator*<>(const Vector& v, int f);
};
// definition of the function template
template<typename T>
Vector<T> operator*(const Vector<T>& v, int f) {
return v;
}
在您的情况下,您直接在 Vector
中直接将 operator*
声明为朋友,而没有任何先前的声明。因此,正确的语法是:
template<typename T>
class Vector {
public:
template<typename>
friend Vector operator*(const Vector& v, int f);
};
template<typename T>
Vector<T> operator*(const Vector<T>& v, int f) {
return v;
}
wandbox上的实时示例
要使模板朋友方法语法工作您需要此模板方法的前向声明。
template<typename T>
class Vector;
template<typename T>
Vector<T> operator*(const Vector<T>& v, int f);
template<typename T>
class Vector
{
template<typename T_> friend
Vector<T_> operator*(const Vector<T_>& v, int f);
};
template<typename T>
Vector<T> operator*(const Vector<T>& v, int f)
{
return v;
}
您使用的任何书都错误地解释了它。
您需要做的是
template<typename T>
class Vector
{
public:
friend Vector<T> operator*(const Vector<T>& v, int f);
};
template<typename T>
Vector<T> operator*(const Vector<T>& v, int f)
{
return v;
}
以上使operator*()
接受Vector<T>
是Vector<T>
的朋友,而不是Vector<U>
的朋友(除非T
与U
相同的类型)。
在类定义中,可以从Vector<T>
中忽略<T>
,但是根据我的经验,人类似乎在说服自己的函数声明和功能定义相互对应时遇到了更多麻烦。所以我通常更喜欢不这样做。...
明确专门化模板时使用<>
语法,但这不是您要做的。例如,具有模板函数;
template <class T> void foo(T) { /* whatever */ }
template<> void foo<int> {/* something specific to int */ }
使用<>
也是C FAQ建议的。
,但是您可以像静态的那样简单地使用模板声明来解决它,只是必须以与类参数不同的参数命名。然后,在单独的定义中,您可以再次使用任何类型名称:
template <typename T>
class Vector {
public:
T i{};
// Typename must be different from the class typename(s).
template <typename T_1>
friend ostream& operator<<(ostream& os, const Vector<T_1>& v);
};
// Typename can be any.
template <typename T>
ostream& operator<<(ostream& os, const Vector<T>& v) {
return os << v.i;
}
实时演示
仅此而已。无需怪异的 <>
在函数声明之间或预定前。
- C++使用 rand 定义函数语法
- QObject::连接不起作用 - 使用函数语法找不到信号
- C++ std::函数语法问题
- 如何在不更改现有函数语法的情况下将普通指针替换为共享指针
- 模板化函数语法错误中使用的模板化类中的嵌套类
- C 变化函数语法
- 返回语句中的构造函数语法
- 复制构造函数语法错误:myclass 没有成员 mymember
- C++.传递给函数.语法问题
- C++可视化工作室函数语法突出显示
- 在 c++ 中移动 2d 数组的构造函数(语法逻辑不清楚):
- c 通过值或指针函数语法
- 正确的朋友模板函数语法
- C++类构造函数语法的解释
- C++ 使用指针移动构造函数(*&&&语法)
- 复制构造函数语法并显示构造函数的值
- 回调函数语法
- 类模板专用化中的成员函数语法
- C++学习函数语法
- 使用模板 C++ 的友元函数语法错误