C++ 格式化异常消息字符串的小技巧

Make C++ Exceptions More Informative

相比其他语言,C++的异常是比较primitive的,没有语言层面的stack-trace, STL里的异常类也很有限. 然而作为Modern C++,异常还是必不可少的,虽然有很多人主张pure error code based error handling, 但是这样会介入control-flow, 也使代码更加复杂. 然而异常的一个不足在于它的constructor的参数是一个字符串而已,很多时候我们希望在异常抛出的时候提供一些context information,比如变量的值等等. 最近看facebook的folly C++ 库得到一点启发,所以动手写了一些utility template functions 来包装异常抛出,同时提供格式化的异常信息。具体代码如下

在异常构造函数中传入格式化字符串提供上下文信息

template  void Throw(TArgs&&... rest) {    throw TExcept(ToStr(std::forward(rest)...).c_str());  }  template  void ThrowOnFalse(TVal&& value, TRest&&... rest) {    if (!value) {      Throw(std::forward(rest)...);    }  }  // enable exception with formatted string message   template  void Throwf(const char* fmt, ...) {    char buf[DEFAULT_BUFSIZE];    va_list ap;    va_start(ap, fmt);    vsnprintf(buf, sizeof buf, fmt, ap);    va_end(ap);    throw E(std::string(buf).c_str());  }

让异常信息自动包含出错位置

一个macro就搞定了,如下

# define THROW_FMT(EXCEPTION, fmt, ...) \   Throwf("[Error] %s:%d:%s:\n" fmt "\n", __FILE__, __LINE__, __func__, ## __VA_ARGS__ )# define CHECK_THROW(cond,E) \  if(!(cond)) \   Throwf("[CheckFailure] %s:%d:%s:\n" "Failed Condition: " # cond , __FILE__,__LINE__,__func__ )

另外,定义Custom Exception也是一个很枯燥的事情,很多时候就是继承std::exception 或者 std::runtime_error 所以写了一个Macro来简化自定义异常类的构造

# define NEW_RT_EXCEPTION(E) class E: public std::runtime_error\    {\  public:\   explicit E(const char* m): runtime_error(m){}\   explicit E(const std::string& m): runtime_error(m){}\   virtual ~E(){}\    }

在之前的代码中,注意到ToStr() 函数,实际上是一个模板函数,用来做 Convert everything to string,是一个受folly启发写的一个简化版本. 其实就是很多函数特化而已,部分代码如下

字符串转换模板函数

///   /// Everything conversion to string  ///   template std::string ToStr(TSrc src) {  std::stringstream ss;  ss inlinestd::string ToStr(double src){  char buf[DEFAULT_BUFSIZE];  d2string(buf, sizeof buf, src);  return std::string(buf);}// variadic template version templatestd::string ToStr(TSrc src, TRest&&... rest) {  std::string r = ToStr(src);  r += ToStr(std::forward(rest)...);  return r;}

c++

版权声明

本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处。如若内容有涉嫌抄袭侵权/违法违规/事实不符,请点击 举报 进行投诉反馈!

相关文章

立即
投稿

微信公众账号

微信扫一扫加关注

返回
顶部