Reputation: 25944
I am trying to overload << operator, so that when I use my class object in std::cout
, it prints out the data members which is supposed to get printed.
I know I have to define a friend functions signature inside of a class, and then outside of the class I define two friend functions doing the job, but I want to hand over the class, and don't want the user to do literally anything and I want the class take care of everything.
How can I achieve such a thing in C++?
Upvotes: 0
Views: 799
Reputation: 137850
C++ is designed to allow non-member functions to do things that would require a member function in other languages. A friend
function is very similar to a member function, in that it can be defined within a class scope. Also (and this can be confusing) if you declare a friend
function only within a class scope, it can only be accessed by passing an object of that class to it.
struct printme {
friend std::ostream &operator<< ( std::ostream &os, printme const & )
{ return os << "hello"; }
friend void named_friend( printme const & ) {}
};
std::cout << printme(); // OK
named_friend( printme() ); // OK
void (*fn_ptr) = named_friend; /* function not found
it can only be found by association with printme */
Although this subtle rule is odd at first, it reflects the idea that nonmember functions can also be encapsulated by the class.
For more info, read up on argument-dependent lookup (ADL).
Upvotes: 2
Reputation: 422
we usually uses << in the following way:
cout<<myobject;
if you make operator<<() a member function of your class you have to use the following syntax to call operator<<()
myobject<<cout;
do you want it that way? if its ok for you , you can make it a member function .
if you want it like
cout<<myobject
- you have to make operator<<() a friend function of your class
Upvotes: 0
Reputation: 13510
Here is an example:
#include <iostream>
#include <string>
using namespace std;
class A {
public:
string pr() { return "Hi, I'm class A"; }
};
ostream &operator << (ostream &o, const A &a) {
o << a.pr();
return o;
}
int main() {
A a;
cout << a << endl;
return 0;
}
However, from my experience, don't do that. Oveloading is academically nice, but it makes it diffult to search your application for its implementation, and even comprehend that << has been overloaded. I always use something of the form cout << myobject.tostring()
Upvotes: -1