Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the difference between flush() and sync() in regard to fstream buffers?

I was reading the cplusplus.com tutorial on I/O. At the end, it says fstream buffers are synchronized with the file on disc

Explicitly, with manipulators: When certain manipulators are used on streams, an explicit synchronization takes place. These manipulators are: flush and endl.

and

Explicitly, with member function sync(): Calling stream's member function sync(), which takes no parameters, causes an immediate synchronization. This function returns an int value equal to -1 if the stream has no associated buffer or in case of failure. Otherwise (if the stream buffer was successfully synchronized) it returns 0.

in addition to a few other implicit cases ( such as destruction and stream.close() )

What is the difference between calling fstream::flush() and fstream::sync()? endl?

In my code, I've always used flush().

Documentation on std::flush():

Flush stream buffer

Synchronizes the buffer associated with the stream to its controlled output sequence. This effectively means that all unwritten characters in the buffer are written to its controlled output sequence as soon as possible ("flushed").

Documentation on std::streambuf::sync():

Synchronize input buffer with source of characters

It is called to synchronize the stream buffer with the controlled sequence (like the file in the case of file streams). The public member function pubsync calls this protected member function to perform this action.

Forgive me if this is a newbie question; I am a noob.

like image 229
cjcurrie Avatar asked Jan 10 '13 06:01

cjcurrie


People also ask

What does fstream flush do?

Flush stream bufferSynchronizes the buffer associated with the stream to its controlled output sequence. This effectively means that all unwritten characters in the buffer are written to its controlled output sequence as soon as possible ("flushed").

What is flushing of stream in CPP?

Flushing a stream ensures that all data that has been written to that stream is output, including clearing any that may have been buffered. Some streams are buffered to aid performance, e.g. a stream writing to disk may buffer until the content reaches a block size.


3 Answers

basic_ostream::flush This is a non-virtual function which writes uncommited changes to the underlying buffer. In case of error, it sets an error flag in the used stream object. This is because the return value is a reference to the stream itself, to allow chaining.

basic_filebuf::sync This is a virtual function which writes all pending changes to the underlying file and returns an error code to signal success or failure.

endl This, when applied to an ostream, writes an '\n' to the stream and then calls flush on that stream.

So, essentially: flush is a more general function for any stream, whereas sync is explicitly bound to a file. flush is non-virtual, whereas sync is virtual. This changes how they can be used via pointers (to base class) in the case of inheritance. Furthermore, they differ in how they report errors.

like image 166
Agentlien Avatar answered Oct 23 '22 23:10

Agentlien


sync is a member of input streams, all unread characters are cleared from the buffer. flush is a member of output streams and buffered output is passed down to the kernel.

like image 23
perreal Avatar answered Oct 23 '22 22:10

perreal


C++ I/O involves a cooperation between a number of classes: stream, buffer, locale and locale::facet-s.

In particular sync and flush are member function that exist in both stream and streambuf, so beware to what documentation you are referring, since they do different things.

On streams flush tells the stream to tell the buffer (note the redirection) to flush its content onto the destination. This makes sure that no "pending write" remains.

std::endl, when applied to thestream with <<, is no more than a

thestream.put('\n'); thestream.flush();

Always on streams, sync tells the stream to tell the buffer to flush the content (for output) and read (for input) as much as it can to refill the buffer.

Note that -in buffers- sync can be also called internally by overflow to handle the "buffer full" (for output) and "buffer empty" (for input) situations.

I thus sense, sync is much more an "internal" function used in stream to buffer communication and buffer implementation (where it is virtual and overridden in different buffer types), while flush is much more an interface between the stream and the client program.

endl ... is just a shortcut.

like image 4
Emilio Garavaglia Avatar answered Oct 24 '22 00:10

Emilio Garavaglia