Polymorphism and ostream &operator<<()
The canonical method for making a class work with ostreams is to declare
a function similar to this:
class NameValuePair;
std::ostream &operator<<(std::ostream &o, const NameValuePair &nvp)
{
return o << nvp.name << "\t" << nvp.value;
}
Where operator<<() might be declared a friend to the class, if it needed
to access an object's internals, or it might not. But in neither case is
it a member function of the class.
Which means that it's not polymorphic.
If I have a reference of type Parent, that is actually referencing an
object of type Child, which is derived from Parent, an attempt to print
the referenced object doesn't work.
Child child;
Parent &parent = child;
std::cout << "Parent = " << parent << std::endl;
This results in the parent's ostream &operator<<() method being called,
and not the child's. Which is probably not what we would want.
One obvious way to make this work is to provide some sort of output
member function within the classes, marked virtual so that we get the
polymorphism we desire, then to implement an ostream &operator<<() on the
parent class that calls that member function:
class Parent;
std::ostream &operator<<(std::ostream &o, const Parent &parent)
{
return o << Parent.to_string();
}
But I can envision situations where this might not be an ideal solution.
If the internal representation of an object might result in a very large
string, this approach could have significant performance penalties.
I'm sure this is an old problem, that many have run into before.
How do folks usually deal with it? Are there any common idioms?
--
The use of COBOL cripples the mind; its teaching should, therefore, be
regarded as a criminal offence.
-- Edsger W. Dijkstra, SIGPLAN Notices, Volume 17, Number 5