I mentioned this back in our earlier emails (http://nagoya.apache.org/eyebrowse/ReadMsg?listName=log4cxx- [EMAIL PROTECTED]&msgNo=272, see point 1), I was surprised when your submission didn't derive from basic_ostream.
You were thinking inheritence and I was thinking delegation. Since we weren't specific, it's not surprising we got it mixed up.
I'm pretty convinced that it is better to be an STL ostream than
> to kind of look like one, even if some things are suboptimal > which I'm not convinced they are.
I think we've identified a number of disadvantages of inheriting from ostream, and I have yet to see one from using delegation (not surprising, delegation tends to be more flexible). I'm probably just missing something.
Let's revisit this after we have some experience with the current
> approach.
Sounds like a good plan.
if (logger->isEnabledFor(myLevel)) { ostringstream buffer; buffer << /* some stuff */; logger->forcedLog(myLevel, buffer.str(), __FILE__, __LINE__); }
Since the stream-based API is a layer over the base API, the stream API can never be faster than the best use of the base API. When we get some more experience, there might be some things that we can tweak, but I'm not ready to obsess over this aspect right now.
My intent was, in the C++ tradition, to find a way to get the higher level of abstraction for a preferred idiom (the code sample I presented above) without imposing any additional overhead. The implementation I presented behaves almost exactly like the example listed above (the exception being buffer is allocated on the heap) and as such the optimizer can generate code which is just as fast.
This API is totally isolated from the rest of the log4cxx design, so deep knowledge of the internals isn't particularly necessary. The difficulty comes that short-circuiting insertion is not desirable for most stream types, so there isn't any support for it in the STL.
Yeah, I guess this is part of the reason I see logstreams as not being ostreams.
>Why? The idea is to do absolutely nothing if the current level is disabled. Why worry about tracking iostate for a stream that is not used?
If you do something like:
logstream << log4cxx::Level::INFO << std::scientific; logstream << "e = " << exp(1.0) << LOG4CXX_ENDMSG;
logstream << log4cxx::Level::WARN << "pi/4 = " << atan(1.0) << LOG4CXX_ENDMSG;
Then the warning message may change depending on whether INFO is enabled. I know that you would like fix the stream to one level, but it may make changing the level of a message non-trivial and it should be trivial.
Isn't this about as easy though?
logstream(logger, log4cxx::Level::INFO) << std::scientific << "e = " << exp(1.0) << LOG4CXX_ENDMSG;
logstream(logger, log4cxx::Level::WARN) << std::scientific << "pi/4 = " << atan(1.0) << LOG4CXX_ENDMSG;
Sure, you have to specify the modifiers each time, but in real world code you'd want to do that anyway. You want to have as few side effects as possible inside your logging code, so you'd want to use Boost's IO state savers if you were going to reuse the stream anyway.
--Chris
