繁体   English   中英

向 std::runtime_error 添加一个额外的字符串

[英]Adding an extra string to std::runtime_error

我想要一个自定义异常,其中嵌入了上下文信息,包括字符串和格式化的what()

例如:

struct MyError : public std::runtime_error {
  MyError(std::size_t line, std::size_t column, std::string expected, std::string found) 
    : std::runtime_error(FormatPrettyMessage(...)), line(line), column(column), expected(expected), found(found) {}
  MyError(const MyError&) = default;
  MyError& operator =(const MyError&) = default;
  ~MyError() = default;

  size_t line;
  size_t column;
  std::string expected; // these are
  std::string found;    // problematic
};

但是, 最佳实践说异常应该有一个noexcept复制构造函数,因为抛出可能涉及隐式复制。

上面不能有noexcept复制构造函数,因为复制字符串会抛出std::badalloc cppreference暗示标准库使用写时复制字符串来避免这种情况( libstdc++确实使用了内部 COW 字符串实现)。

但是外行人应该如何按照习惯将字符串成员添加到他们的自定义异常中呢? 尝试序列化我的数据并将其填充到runtime_error消息中,正如这个答案所建议的那样,感觉很老套并强制异常处理代码解析和重新格式化what() output。但是将整个自定义字符串扔到我的小项目中只是为了制作一个例外感觉很过分。

您可以移动字符串而不是复制它们,特别是因为您一开始就按值将它们传递给构造函数,所以在您的构造函数进入之前它们已经被调用者复制了。 std::string移动构造函数被标记为noexcept

MyError(std::size_t line, std::size_t column, std::string expected, std::string found) 
    : std::runtime_error(FormatPrettyMessage(...)), line(line), column(column), expected(std::move(expected)), found(std::move(found)) {}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM