Hello ladies and gents,

In my book, I'm currently reading about the use of creating your own operators << and >> for in- &output.

There's been given a small example that goes like this:

#include <iostream>

using namespace std;

class vec 
{ 
public:
   vec(float x1=0, float y1=0) {x = x1; y = y1;}

   vec operator+(const vec &b) const
   {  
	   return vec(x + b.x, y + b.y);
   }

   float x, y;
};

ostream &operator<<(ostream &os, const vec &v)
{  
	return os << v.x << "   " << v.y << endl;
}

istream &operator>>(istream &is, vec &v)
{  
	float x, y;

	is >> x >> y;
	v = vec(x, y);

	return is;
}

int main()
{  
	vec u, v, s;
	cout << "Typ twee getallenparen:\n";
	cin >> u >> v;
	s = u + v;    // Vectoroptelling 
	cout << "De som bij vectoroptelling is:\n"
		 << s;

   return 0;
}

But, what is actually the benefit of writing it this way, when you could write it like this aswell?

#include <iostream>

using namespace std;

class vec 
{ 
public:
	vec(float x1=0, float y1=0) {x = x1; y = y1;}

	void printvec() const
	{
		cout << x << "  " << y << endl;
	}

	vec operator+(const vec &b) const
	{
		return vec(x + b.x, y + b.y);
	}

private:
   float x, y;
};

int main()
{  
	vec u(3, 1), v(1, 2), s;

	s = u + v;    // Vectoroptelling!

	s.printvec(); // Uitvoer: 4  3

   return 0;
}

Could someone explain what the actual benefit would be to use self defined << >> operators :?:

because the destination of your << operator in the end will not always been the console, so you shouldn't assume that cout covers your function's usage.

(for example, it might be sent to a file, it might be sent on a network connection, etc... you just code it once to send out an ostream and whatever other functions accept an ostream will be able to use it. If you merely do cout in your code, you're limiting yourself...)

Thanks for the help winbatch,

So, if I understand you correctly and explaining it in my own words, the advantage of using self defined in- & output operator is that you can actually send data towards other programs, is that correct?

I would term it as other destinations rather than other programs. You can also 'chain' things for example (using your vec class):

vec v;
cout << "Here comes my vector:"<<v<<" etc...";

You should ignore those examples. They use public data members and do not show fully correct technique. If you do things this way then once you have private members the operators << and >> will have to be friends. This is also not desirable. There is a better idiom. Illustrated here...

class Base 
{
   public:
      ostream& print( ostream& os)const
      {
         return do_print(os);
      }
   protected:
      virtual ostream& do_print(ostream&)const = 0;
};

ostream& operator << ( ostream& os, const Base& object)
{ 
   return object.print(os);
}

class Derived: public Base
{
   protected:
      virtual ostream& do_print( ostream& os )const
      { 
         // send objects data members to the stream here then...
         return os;
      }
};

Thanks for your example Stoned_coder. So, the correct way of dealing with something like this is to use polymorphism then, atleast, that's what I can make out of your example correct :?:

In a simple example with a concrete underived class it isnt necessary but when you have hierarchys with many concrete classes this idiom works a charm.You have a public function that specifies an invarient over the hierarchy that objects can print themselves to an ostream. The actual printing is handled in each derived class that provides an override for the do_print function. This also means that operator << can be loosely coupled to our class rather than tightly coupled.I illustrated the full idiom. Im sure anyone with an ounce of savvy can work out a version for a single class.
This is nothing more than dependancy management. We have stopped operator << from depending on the privates on an object.

This article has been dead for over six months. Start a new discussion instead.