如何使用友元函数重载 operator == outside template class?
how to overload operator == outside template class using friend function?
我正在尝试编写一个重载 operator== 的模板 class。我知道如何将它放入 class:
template <typename T>
class Point
{
private:
T x;
public:
Point(T X) : x(X) {}
bool operator== (Point &cP)
{
return (cP.x == x);
}
};
但是现在我想在模板之外实现这个class。我读过这个 post:
并在我的代码中添加模板声明:
template <typename> class Point;
template <typename T> bool operator== (Point<T>, Point<T>);
template <class T>
class Point
{
private:
T x;
public:
Point(T X) : x(X) {}
friend bool operator== (Point cP1, Point cP2);
};
template <class T>
bool operator== (Point<T> cP1, Point<T> cP2)
{
return (cP1.x == cP2.x)
}
然而我仍然得到一个错误:unresolved external symbol "bool __cdecl operator==(class Point<int>,class Point<int>)" (??8@YA_NV?$Point@H@@0@Z) referenced in function _main
当我从 :
带走 朋友
friend bool operator== (Point cP1, Point cP2);
并希望它是成员函数,会出现另一个错误:
too many parameters for this function
为什么?
你必须将 friend
class 放在彼此内部,以及它们内部。 Real 的命名在句法上相同,没有替换表达式。所以 friend bool operator==(P<T>,P<T>);
进入两个 classes。所以把 friend
放在 class T :-)
的 bool 之前
这是一个棘手的问题:class 中的友元声明将为每个实例 定义一个不同的 友元函数你的 class。换句话说,Point<int>
和 Point<double>
会产生 2 个不同的非模板友元函数。另一方面,外部函数是一个模板函数,与 class 内部的 friend
无关。解决方法:在class里面定义友元函数。由于 friend name injection, it will be found successfully by ADL.
operator==()
的声明是一个模板。 friend
的声明是 不是 模板而是非模板。要使模板 operator==()
成为好友,您还需要将好友声明也设为模板:
template <typename T> class Point;
template <typename S>
bool operator== (Point<S>, Point<S>);
template <typename T>
class Point {
// ...
template <typename S>
friend bool operator== (Point<S>, Point<S>);
};
@Kühl 的回答是声明模板化 class 的模板化友元函数的最宽松方法。但是,这种方法有一个不明显的副作用:Point
的所有模板实例都是 operator==()
的所有模板实例的朋友。另一种方法是仅将具有相同类型 Point
的实例化为朋友。这是通过在 operator==()
.
的友元声明中添加一个 <T>
来完成的
template <typename T> class Point;
template <typename S>
bool operator== (Point<S>, Point<S>);
template <typename T>
class Point {
// ...
friend bool operator==<T> (Point, Point);
};
我正在尝试编写一个重载 operator== 的模板 class。我知道如何将它放入 class:
template <typename T>
class Point
{
private:
T x;
public:
Point(T X) : x(X) {}
bool operator== (Point &cP)
{
return (cP.x == x);
}
};
但是现在我想在模板之外实现这个class。我读过这个 post:
template <typename> class Point;
template <typename T> bool operator== (Point<T>, Point<T>);
template <class T>
class Point
{
private:
T x;
public:
Point(T X) : x(X) {}
friend bool operator== (Point cP1, Point cP2);
};
template <class T>
bool operator== (Point<T> cP1, Point<T> cP2)
{
return (cP1.x == cP2.x)
}
然而我仍然得到一个错误:unresolved external symbol "bool __cdecl operator==(class Point<int>,class Point<int>)" (??8@YA_NV?$Point@H@@0@Z) referenced in function _main
当我从 :
带走 朋友friend bool operator== (Point cP1, Point cP2);
并希望它是成员函数,会出现另一个错误:
too many parameters for this function
为什么?
你必须将 friend
class 放在彼此内部,以及它们内部。 Real 的命名在句法上相同,没有替换表达式。所以 friend bool operator==(P<T>,P<T>);
进入两个 classes。所以把 friend
放在 class T :-)
这是一个棘手的问题:class 中的友元声明将为每个实例 定义一个不同的 友元函数你的 class。换句话说,Point<int>
和 Point<double>
会产生 2 个不同的非模板友元函数。另一方面,外部函数是一个模板函数,与 class 内部的 friend
无关。解决方法:在class里面定义友元函数。由于 friend name injection, it will be found successfully by ADL.
operator==()
的声明是一个模板。 friend
的声明是 不是 模板而是非模板。要使模板 operator==()
成为好友,您还需要将好友声明也设为模板:
template <typename T> class Point;
template <typename S>
bool operator== (Point<S>, Point<S>);
template <typename T>
class Point {
// ...
template <typename S>
friend bool operator== (Point<S>, Point<S>);
};
@Kühl 的回答是声明模板化 class 的模板化友元函数的最宽松方法。但是,这种方法有一个不明显的副作用:Point
的所有模板实例都是 operator==()
的所有模板实例的朋友。另一种方法是仅将具有相同类型 Point
的实例化为朋友。这是通过在 operator==()
.
<T>
来完成的
template <typename T> class Point;
template <typename S>
bool operator== (Point<S>, Point<S>);
template <typename T>
class Point {
// ...
friend bool operator==<T> (Point, Point);
};