Visualization Tool Kit(VTK)など

×

公式ドキュメントの補足

Global logger objects

BOOST_LOG_INLINE_GLOBAL_LOGGER(type_name, source_type)
BOOST_LOG_INLINE_GLOBAL_LOGGER_CTOR_ARGS(type_name, source_type, ctor-arguments)

BOOST_LOG_INLINE_GLOBAL_LOGGER(global_logger, boost::log::sources::logger)
BOOST_LOG_INLINE_GLOBAL_LOGGER_CTOR_ARGS(global_channel_logger, boost::log::sources::channel_logger<>, (boost::log::keywords = "channel"))

void func()
{
  BOOST_LOG(global_logger::get()) << "Logging by using global_logger";
  BOOST_LOG(global_channel_logger::get()) << "Logging by using global_channel_logger";
}

これはtype_nameという名前のクラスを生成するマクロであるから名前空間を使えば下記のようなことができる.

namespace A {
  BOOST_LOG_INLINE_GLOBAL_LOGGER_CTOR_ARGS(logger, boost::log::channel_logger<>, (boost::log::keywords = "namespace A"));
  
  void func() {
    BOOST_LOG(logger::get()) << "Message from namespace A";
  }
}

namespace B {
  BOOST_LOG_INLINE_GLOBAL_LOGGER_CTOR_ARGS(logger, boost::log::channel_logger<>, (boost::log::keywords = "namespace B"));

  void func() {
    BOOST_LOG(logger::get()) << "Message from namespace B";
  }
}

BOOST_LOG_FUNCTION in MSVC

MSVCでNamed Scope属性を使うときに,BOOST_LOG_FUNCTIONは機能しない(boost/current_function.hppがなぜか実装していない)ため,下記のように書けばよい.

BOOST_NAMED_SCOPE(__FUNCTION__)

基本属性とその型

予め定義してある属性は概ね下記の通り.
attribute_nametypedescription
"Severity"enum
"Channel"string
"Scope"named_scope_listnamed_scope_entryの階層リスト.frontが浅層,backが深層.
named_scope_entryスコープ名,ファイル名,行番号を保有する構造体.
BOOST_LOG_FUNCTION, BOOST_NAMED_SCOPEで記録される.
"Message"string
wstring
logger系はstringを,wlogger系はwstringでデータをセットする.

sinkで属性を取り出す

record_viewから各属性値を取り出す.

typedescription
attribute_value_set属性の文字列リテラルとattribute_valueのmap
attribute_value属性値の入れ物.extract<type>()で取り出しを試みる.戻り値はoptional.


class attribute_extraction_sink_backend : public sinks::basic_sink_backend<sinks::synchronized_feeding>
{
  public:
    void consume(logging::record_view const& rec);
}

void attribute_extraction_sink_backend::consume(logging::record_view const& rec)
{
  int sev;
  std::string ch;
  std::string deepest_scope_name; // extract the deepest scope
  std::string file_name;
  unsigned int line_number;
  std::string message;

  auto& attr_val_set = rec.attribute_values();
  {
    auto& mapped_value = attr_val_set["Severity"];
    if (mapped_value) sev = mapped_value.extract<severity_level>().get();
  }

  {
    auto& mapped_value = attr_val_set["Channel"];
    if (mapped_value)  ch = mapped_value.extract<string>().get();
  }

  {
    auto& mapped_value = attr_val_set["Scope"];
    if (mapped_value)
    {
      auto scope_list = mapped_value.extract<named_scope_list>();
      if (scope_list && scope_list.size())
      {
        auto deepest_scope = scope_list.back();
        deepest_scope_name = deepest_scope.scope_name;
        file_name = deepest_scope.file_name;
        line_number = deepest_scope.line;
      }
    }
  }

  {
    auto& mapped_value = attr_val_set["Message"];
    if (mapped_value)
    {
      if(auto try_string = mapped_value.extract<string>())
      {
        message = try_string.get();
      }
      else if(auto try_wstring = mapped_value.extract<wstring>())
      {
        auto wessage = try_wstring.get();
        // 環境に適合した方法でwstringからstringに変換する
      }
    }
  }
}

sourceでfilteringする

例えばReleaseビルドではストリームでの処理が無駄なのでsinkで見えないようにするだけでなくdebugログをそもそも行わないように設定したい.

enum severity_level { Debug, Info, Warning, Error, Fatal }
class severity_filtering_logger : public basic_composite_logger<char, severity_logger<severity_level>, single_thread_model, features<severity<severity_level>>>
{
  typedef basic_composite_logger<char, severity_logger<severity_level>, single_thread_model, features<severity<severity_level>>> base;
  public:
    BOOST_LOG_FORWARD_LOGGER_MEMBERS_TEMPLATE(severity_filtering_logger);
    template< typename ArgsT >
    boost::log::record open_record(ArgsT const& args)
    {
      if (args[boost::log::keywords::severity | base::default_severity()] < filtering_level) return boost::log::record();
      return base::open_record(args);
    }
    inline severity_level get_filtering_level() const { return filtering_level; }
    inline void set_filtering_level(severity_level val) { filtering_level = val; }
  private:
    severity_level filtering_level = severity_level::Info;
};

// sample
severity_filtering_logger logger;
BOOST_LOG_SEV(logger, severity_level::info) << "Info"; // 表示される
BOOST_LOG_SEV(logger, severity_level::debug) << "Debug"; // 表示されない

通常のBOOST_LOG_SEVでロギングすればよい.

MSVC(Windows?)におけるWide Character Logging/Output

#大きな勘違いをしていたため修正

下記が必要.これはboost.logに関係なくcout, wcoutでも必要.
sink->imbueは必要ない.

std::locale::global("japanese_japan.932");

補足
  • テキストファイルとしてのソースの文字コード
  • プログラムとしてchar文字列リテラルの文字コード

は同一ではない.
なお,C++11から導入されたUnicode String Literalはvs2013(c120), 2013 Nov CTP共に未実装である.

DLLでの利用

シングルトンであるため,boost_logのスタティックライブラリを各DLLにリンクしてしまうと複数のcoreが生成されてしまう.
BOOST_DYN_LINKではだめでBOOST_ALL_DYN_LINKをdefineすること.

コメントをかく


「http://」を含む投稿は禁止されています。

利用規約をご確認のうえご記入下さい

Menu

メニュー

チュートリアル

アルゴリズム(数学)

並列計算

STL

#include<memory> #include<string> #include<sstream> #include<algorithm> #include<functional> #include<numeric>

Media Foundation

【メニュー編集】
Wiki記法ガイド

メンバーのみ編集できます

広告募集中