我想重载运算符<<在我的一个课程中。 签名是这样的:
friend std::ostream& operator<<(std::ostream& os, const Annuaire& obj)
当我尝试在.cpp文件中定义它时,它表示运算符&lt;&lt;确切地说需要1个参数,但是,当我在.h中定义它时,它编译/工作正常。
这是我在.cpp文件中定义它的方式:
std::ostream& Annuaire::operator<<(std::ostream& os, const Annuaire& obj){ // ... }
是否与需要在头文件中定义的朋友功能有关?
答案 0 :(得分:12)
它可以在cpp文件中定义,但它至少需要在头文件中声明,否则你想要使用它的所有地方都只会看到流本身给你的东西,而不是你的过载。
// .h and in class
friend std::ostream& operator<<(std::ostream& os, MyClass const& v);
// .cpp
std::ostream& operator<<(std::ostream& os, MyClass const& v){
// print it
}
答案 1 :(得分:9)
问题在于你定义它的方式。它不是该类的成员,它只是该类的朋友。您需要删除Annuaire::
前缀。所以,改变这个:
std::ostream& Annuaire::operator<<(std::ostream& os, const Annuaire& obj){ // ...
到此:
std::ostream& operator<<(std::ostream& os, const Annuaire& obj){ // ...
错误消息的原因是Annuaire::operator<<(std::ostream& os, const Annuaire& obj)
期望三个参数:它被调用的Annuaire
实例(作为this
),以及另外两个参数({{1 }和os
)。
答案 2 :(得分:5)
如David的回答所述,在这种情况下,运算符不是成员函数,它只是同一名称空间中的友元函数。这使我指出了解决非常类似问题的正确方向。
我发布这个答案是因为它对我来说并不是很明显。也许是因为我添加运算符的实现文件没有完全包含在命名空间中,而是使用了using指令。
不应该是相关的,但我正在使用VS2013。
//Foo.h
namespace Bar{
class Foo
{
public:
Foo();
private:
int n;
friend std::ostream & operator<<(std::ostream &, Foo const &);
};
}
//Foo.cpp
using namespace Bar; //won't apply to the operator definition
Foo::Foo(){}// doesn't require the Bar qualifier because of the using-directive
//the operator required the Bar namespace qualifier
std::ostream & Bar::operator<<(std::ostream & o, Foo const & x)
{
return o << x.n;
}
答案 3 :(得分:3)
朋友函数,即使它们似乎在类中声明,也不是成员函数,而是名称空间级函数(在封闭的命名空间中)。在您的代码中,您正确声明了友元函数,但您尝试将其定义为类的成员函数:
std::ostream& Annuaire::operator<<(std::ostream& os, const Annuaire& obj){
该定义适用于Annuaire
的成员函数,称为operator<<
,它带有两个参数,这两个参数无效,因为operator<<
可以通过以下两种方式之一重载:自由函数采用两个参数(左手侧和右手侧)或作为类的成员函数,出现在表达式的lhs中,采用rhs类型的参数。在这种特殊情况下,由于lhs是std::ostream
并且您无法修改它,因此您只能选择使用自由函数:
std::ostream& operator<<(std::ostream& os, const Annuaire& obj)
答案 4 :(得分:2)
没有这样的限制;你可能只是写错了。应该是这样的:
class Foo
{
int n;
friend std::ostream & operator<<(std::ostream &, Foo const &);
};
std::ostream & operator<<(std::ostream & o, Foo const & x)
{
return o << x.n;
}