Boost logo

Boost :

From: Andreas Harnack (ah.boost.04_at_[hidden])
Date: 2007-11-21 09:07:48


Hi @,

does anybody know why the ostream_iterator class has been mad a
template if a template just for the assignment operator would
have been sufficient? I.e., why does it say:

     template<class T>
     ostream_iterator
     {
             ...
         public:
             ostream_iterator& operator=(T const&);
             ...
     };

instead of

     ostream_iterator
     {
             ...
         public:
             template<class T>
             ostream_iterator& operator=(T const&);
             ...
     };

or possibly:

     template<class os=std::ostream>
     ostream_iterator
     {
             ...
         public:
             typedef typename os::char_type char_type;
             typedef typename os::traits_type traits_type;
             typedef os ostream_type;

             template<class T>
             ostream_iterator& operator=(T const&);
             ...
     };

In my compiler version (g++ 3.0 and g++ 3.4) the type T is used
nowhere else.

As a consequence I have to specify

     myContainer v;
     copy(v.begin(), v.end(),
         ostream_iterator<myContainer::value_type>(cout, "\n"));

while it just could be:

     copy(v.begin(), v.end(), ostream_iterator(cout, "\n"));

or

     copy(v.begin(), v.end(), ostream_iterator<>(cout, "\n"));

The answer is obvious for istream_iterators: They provide their
input values through the operator*() and have, giving the fact
that it does not take any argument, no way to deduce the
required return type, so it needs to be specified explicitly.
That's different for ostream_iterators. They get their output
values as arguments and are perfectly capable of deducing their
type, so requiring it as an explicit template argument seems to
be an unnecessary over-specification.

One could argue, that the template argument adds to type safety,
but that sound rather weak to me, especially if standard streams
are involved. After all, std::cout and std::cerr are both
global, so there's nothing at all to prevent me from printing to
them from anywhere else in my application, even from a call
implicitly made by function used in the expression above; let
alone threads or other operating system processes.

So, it seems to me, that the template argument does not provide
any additional value but only makes the expression above
unnecessary complicate. Am I missing something?

Thanks,
Andreas


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk