为什么Boost Log日志操作不是const的?

3
我试图使用一个severity channel logger,但我遇到了BOOST_LOG_SEV不是常量方法的问题——我想这是由于open_record()和push_record()两者的原因。
这基本上会强制我将我的所有类方法都不设置为const,因为它们要向其记录器写入信息。我真的负担不起这样做——所以我目前受限于全局记录器。
在我的当前实现中,每个类都有一个记录器,其中类名作为信道(在它们的构造函数中初始化),并且它可以在任何时候发出带有 BOOST_LOG_SEV(this->logger, level)的日志消息。
我很想听听非常数性背后的原因,以及我的设计是否符合Boost::Log的意图。

Boost毕竟是开源的,所以您可以直接查阅源代码。我想这比提问并等待答案会更快。 - Alexander Shukaev
它们不能是非const的,因为它们会改变状态。但如果日志记录器是线程安全的,则它们是使用mutable关键字的完美示例。日志记录器是非const、线程安全的成员,不会影响对象的状态。 - John5342
那么是否有更好的设计呢?将记录器设为类成员是不可行的,因为我必须使每个方法都非const。 - Carneiro
2
将记录器设置为可变类成员 mutable SomeLoggerType my_logger;。然后您就可以在非const成员中修改它了。这正是可变的用途所在。 - John5342
啊,可以了,谢谢!(如果您打出来的话)但是在const方法中使用可变成员变量的整个过程不是一个很大的“代码异味”吗? - Carneiro
如果更改可变成员会更改对象的逻辑状态(尽管在C++11中它与线程安全一样重要),那么这就是代码异味。 - John5342
1个回答

5
记录器不能是常量,因为它们会改变自身的状态。如果记录器是线程安全的,并且不改变对象的逻辑状态,则使用mutable关键字是一个完美的例子。
将记录器声明为可变的类成员mutable SomeLoggerType my_logger;,然后您可以在const函数中修改它。这正是mutable的用途。
至于您对mutable是坏代码的看法,mutable就是一种逃生口,专门针对这种情况使用。当您实际上不修改对象的逻辑状态(并在C++11内部同步)时,mutable是非常好的。另一个很好的mutable用法是缓存。

感谢Igor的编辑。这会教会我在手机小屏幕上快速回答问题。 - John5342

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接