'Check if a given ostream object has been written to

Can I query an ostream object about whether or not it has been written to? For an ostringstream, one could use

if(!myOssObject.str().empty())

What about the general case, e.g. an ofstream or cout or cerr?



Solution 1:[1]

In general No.

You can find out how many char (or something else) is written before flushing (sending out the buffered data) by tellp():

Returns the output position indicator of the current associated streambuf object.

cout << "123";

if (cout.tellp() > 0)
{
    // There is some data written
}

After flushing, these output streams will forget what they've written but the last state flags.

If the output device is a real-time and doesn't buffer anything, tellp can't help.

Solution 2:[2]

It's possible, but only if you can get your hands on the stream beforehand. The only generally guaranteed solution is to insert a filtering streambuf, which keeps track of the number of characters output:

class CountOutput : public std::streambuf
{
    std::streambuf* myDest;
    std::ostream*   myOwner;
    int myCharCount;    //  But a larger type might be necessary

protected:
    virtual int overflow( int ch )
    {
        ++ myCharCount;
        return myDest->sputc( ch );
    }

public:
    CountOutput( std::streambuf* dest )
        : myDest( dest )
        , myOwner( nullptr )
        , myCharCount( 0 )
    {
    }
    CountOutput( std::ostream& dest )
        : myDest( dest.rdbuf() )
        , myOwner( &dest )
        , myCharCount( 0 )
    {
        myOwner->rdbuf( this );
    }
    ~CountOutput()
    {
        if ( myOwner != nullptr ) {
            myOwner.rdbuf( myDest );
        }
    }

    int count() const
    {
        return myCount;
    }
};

As usual, this can be used with just about any std::ostream:

CountOutput counter( someOStream );
//  output counted here...
int outputCount = counter.count();

When it goes out of scope, it will restore the original state of the stream.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 Marc Dirven