[Apologies to the computer scientist who came up with that phrase
(w.r.t. GOTOs)]
I haven't looked at the serialization library that was just up for
review, but some of the comments I saw on this list suggested that the
archive classes use virtual operators for reading or writing the basic
types. I have a book called _C++ FAQs_ (2nd ed.) that has a blurb
about a virtual assignment operator. I think the concept is too funky
because:
1. You have no choice about an operator's interface, even if that
interface isn't the best for inheritance.
2. The dispatch interactions could introduce subtleties.
I have a better idea: use the "concrete function calls a virtual
function" idiom. Maybe it could be like:
class my_writer
{
public:
//...
// The main writing functions; they secretly call their private
// do_write version;
my_writer & operator <<( char x );
my_writer & operator <<( signed char x );
my_writer & operator <<( unsigned char x );
my_writer & operator <<( signed short x );
my_writer & operator <<( unsigned short x );
my_writer & operator <<( unsigned x );
my_writer & operator <<( int x );
my_writer & operator <<( unsigned long x );
my_writer & operator <<( signed long x );
my_writer & operator <<( float x );
my_writer & operator <<( double x );
my_writer & operator <<( long double x );
my_writer & operator <<( wchar_t x );
#ifdef Long-Longs
my_writer & operator <<( unsigned long long x );
my_writer & operator <<( signed long long x );
#endif
my_writer & operator <<( void *x );
// do cv-variants too; all of them call the void* version
template < typename T >
my_writer & operator <<( T *x );
// don't do this, explode T for char, signed char, unsigned char,
// and wchar_t; they determine the string length, then call the
// same private do_write function the singleton versions do
template < typename T >
my_writer & write_as_string( T *x );
// don't do this, use the N-argument only and explode T for
// each basic type; they call the same private do_write function
// the singleton versions do
template < typename T, std::size_t N >
my_writer & write_as_array( T (&a)[N] );
private:
// don't do this, explode T for each basic type
// (actually, you can't do this since virtual & templates don't mix)
template < typename T >
virtual void do_write( T *a, std::size_t n = 1 );
};
Remember that this idiom allows pre- and post-processing around the
virtual call, without the override's author being able to
(accidentally) kill that processing.
Daryle
_______________________________________________
Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost
- Re: [boost] Virtual operators considered harmful Daryle Walker