Skip to content

Instantly share code, notes, and snippets.

@dgodfrey206
Last active January 3, 2016 10:09
Show Gist options
  • Save dgodfrey206/8447788 to your computer and use it in GitHub Desktop.
Save dgodfrey206/8447788 to your computer and use it in GitHub Desktop.
Opting in or out of the flushing mechanism of std::endl
#include <iostream>
static int disable() {
static int index(std::ios_base::xalloc());
return index;
}
class save_buffer
{
public:
save_buffer(std::ios& other)
: str(other), buf(other.rdbuf())
{ }
~save_buffer() { str.rdbuf(buf); }
private:
std::ios& str;
std::streambuf* buf;
};
class syncing_buffer_optional : public std::streambuf, public save_buffer
{
public:
syncing_buffer_optional(std::ostream& other)
: save_buffer(other),
buf(other.rdbuf()),
disable_sync(other.iword(disable()))
{ }
std::streambuf::int_type overflow(std::streambuf::int_type c)
{
buf->sputc(c);
return 0;
}
int sync()
{
return disable_sync? 0: buf->pubsync();
}
private:
std::streambuf* buf;
bool disable_sync;
};
std::ostream& flush_on_endl(std::ostream& os)
{
os.iword(disable()) = false;
return os;
}
std::ostream& noflush_on_endl(std::ostream& os)
{
os.iword(disable()) = true;
return os;
}
std::ostream& endl(std::ostream& os)
{
syncing_buffer_optional eb(os);
os.rdbuf(&eb);
return os << std::endl;
}
int main()
{
std::cout << noflush_on_endl << endl;
}
@dgodfrey206
Copy link
Author

Note: I needed to create an endl function because of the lifetime dependencies between the buffer and the stream. Moreover, even if the buffer was static, how can we distinguish between an std::endl call and an arbitrary flush()?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment