[英]Friend function defining an ostream operator
I would like to define an ostream operator to let me easily output variables of type alglib::complex
. 我想定义一个ostream运算符,以方便我输出
alglib::complex
类型的变量。 To provide a working example without including the alglib library I'll instead overload the output of complex<double>
below (this clarification because of an earlier version of the question). 为了提供一个不包含alglib库的有效示例,我将在下面重载
complex<double>
的输出(此澄清是由于问题的早期版本)。 In the header file "my_class.h" I have 在头文件“ my_class.h”中,我有
using namespace std;
#include <complex>
#include <iostream>
class my_class {
public:
ostream& operator << (std::ostream& os, complex<double> a) {
os << "(" << real(a) << "," << imag(a) << ")";
return os;
}
void output(complex<double>);
my_class() {}
~my_class() {}
};
And in the source file "my_class.cpp" I have 在源文件“ my_class.cpp”中,
#include "my_class.h"
void my_class::output(complex<double> cd) {
cout << cd << endl;
}
Finally I have a main method file "run_my_class.cpp": 最后,我有一个主要的方法文件“ run_my_class.cpp”:
#include "my_class.h"
int main(int argc, const char* argv[]) {
my_class obj;
complex<double> cd=complex<double>(1.0,-1.0);
obj.output(cd);
}
I try to compile using 我尝试使用编译
g++ -c my_class.cpp
but this gives me the error 但这给了我错误
my_class.h:9:62: error: ‘std::ostream& my_class::operator<<(std::ostream&, std::complex<double>)’ must take exactly one argument
ostream& operator << (std::ostream& os, complex<double> a) {
However, if I define the operator as a friend, namely friend ostream& operator << (std::ostream& os, complex<double> a)
, it compiles and I compile the main method: 但是,如果我将运算符定义为朋友,即
friend ostream& operator << (std::ostream& os, complex<double> a)
,它将编译并编译main方法:
g++ run_my_class.cpp my_class.o -o run_my_class
And it works as it should. 它可以正常工作。 However this is not what it seems the
friend
keyword is for. 但是,这似乎不是
friend
关键字的用途。 Is there a better way to make this work? 有没有更好的方法可以使这项工作?
Since operator <<
will be called on an std::ostream
, you cannot define this procedure as a member function for my_class
, you have to define it as a global function , since it's an operation for std::ostream
, not my_class
. 由于
operator <<
将在std::ostream
上调用,因此您不能将此过程定义为my_class
的成员函数 , my_class
必须将其定义为全局函数 ,因为它是std::ostream
的操作,而不是my_class
。
By putting the friend
keyword into the declaration, you are saying that you want to declare the operator <<
as a friend global function (not a member function!). 通过将
friend
关键字放入声明中,意味着您要声明operator <<
作为朋友全局函数 (而不是成员函数!)。 The C++ standard lets you put the definition of the friend function there, but it won't be a member function. C ++标准允许您在其中放置friend函数的定义,但它不会成为成员函数。 It is the same as the following, which is more clear:
它与以下内容相同,但更清楚:
#include <complex>
#include <iostream>
class my_class {
public:
friend ostream& operator << (std::ostream& os, complex<double> a);
void output(complex<double>);
my_class() {}
~my_class() {}
};
std::ostream& operator << (std::ostream& os, complex<double> a) {
os << "(" << real(a) << "," << imag(a) << ")";
return os;
}
As it was already pointed out in the comments, the usage of friend
is not necessary here. 正如评论中已经指出的那样,在这里不需要使用
friend
。
Irrelevant to the question, but please be aware that resolving namespaces in a header file is generally a really-really bad idea, since all other files including it will implicitly resolve that namespace too. 与问题无关,但是请注意,解析头文件中的名称空间通常是一个真正的坏主意,因为包括它在内的所有其他文件也会隐式地解析该名称空间。 It can easily lead to vexing compilation errors in the long run.
从长远来看,它很容易导致令人讨厌的编译错误。
I wouldn't call it a better way but a more clear way. 我不会称其为更好的方法,而是更清晰的方法。
Here's your stream operator again: 这又是您的流运算符:
ostream& operator << (std::ostream& os, complex<double> a) {
os << "(" << real(a) << "," << imag(a) << ")";
return os;
}
Its first parameter is the output stream. 它的第一个参数是输出流。 Since you do not have access to the output stream, you can't use the output stream operator as a member function unless you make it a friend of the class.
由于您无权访问输出流,因此除非将其设为该类的朋友,否则不能将输出流运算符用作成员函数。
If you want to want to avoid using friend you can always define it as a function external to the class, and that is the most common way. 如果要避免使用friend ,则可以始终将其定义为类外部的函数,这是最常见的方法。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.