C ++相当于perror?

时间:2015-09-24 08:04:34

标签: c++ error-handling

据我所知,处理流错误的两个选项是perror和流异常。两种选择都是不可取的这就是原因:

PERROR

  • std::strerror返回实现定义的消息。此消息在所有系统上并不总是有用

  • std::strerror不是线程安全的

  • std::strerror返回的指针可以无效

  • C库技术上已被弃用"在C ++中。几乎总是一个C ++ - 等同于。当没有潜在的C ++等价物时,我没有理由依赖POSIX和C

流异常

  • 例外情况不适合每个程序

  • 虽然std::strerror有时可以提供有用的错误消息,但流永远不会提供有用的错误消息。对于f.exceptions(f.failbit),无论是打开文件失败还是无法解压缩,引发的异常都是std::ios_base::failurewhat()是" basic_ios::clear"。

SYSTEM_ERROR

std::ios_base::failure替换std::system_error会产生完全相同的结果。如果我们看一下N2769: Detailed Reporting for Input/Output Library Errors (Revision 2),我们可以看到原因:

  

当抛出ios_base::failure例外时,实现是   鼓励提供ec的值,以确定具体原因   为了失败。 [ 注意 - 操作产生的错误   系统通常会报告为system_category错误   操作系统报告的错误号的错误值。   流库中出现的错误通常是   报告为error_code(ioerrc::stream, iostream_category) - 结束   注意 ]。

     

以上措辞只为规范性鼓励实施者做正确的事情,因而依赖于市场力量   以及实施者的良好意图,以产生有用的结果   用户。任何更强大的东西(比如改变"都会被鼓励到#34; to   "将")需要更多的额外规范,超出了   LWG可以实际解决C ++ 0x的范围。

另一种选择是潜在地依赖庞大的第三方图书馆(我看着你Boost)或者手工推广它(除非你知道自己在做什么,否则你永远不想做。我正在寻找C ++标准库的方法来做到这一点。有没有?

2 个答案:

答案 0 :(得分:1)

我不同意你的意见

  

perror等人是C标准库的成员,因此在技术上已弃用(*)。

即使在cplusplus.com上,如果不是官方文档来源,我也会看到errno:

  

C ++ 11扩展了在此标头中定义所需的基本值集...在C ++中,errno始终声明为宏,但在C中,它也可以实现为具有外部链接的int对象。

我对这些句子的理解是{C} 11中仍然考虑errno

我甚至可以看到以后

  

支持多线程的库应该在每个线程的基础上实现errno:每个线程都有自己的本地errno。这是符合C11和C ++ 11标准的库中的要求。

这意味着即使strerror()不是线程安全的,errno也适用于符合C ++ 11的实现。

如果您愿意,现在由您在同步函数中使用std::strerror(例如使用互斥锁保护)来构建std::string。但无论如何,即使strerror上的每个文档都声明它使用了一个可以被覆盖的静态缓冲区(这就是Posix 1定义strerror_r的原因),我在perror上找不到任何警告保护线安全。

(*)我的意见就是每当OO和模板可以提供更好的界面(iostream vs stdio.h或string vs string.h)时,C库的元素是< em>被C ++库中的其他人替换。但是当没有任何东西可以添加(cerrno,cmath,csignal等)时,C标准库中的函数只包含在C ++库中。

答案 1 :(得分:0)

POSIX有strerror_r(),Windows有strerror_s()。请注意,有一些名为strerror_r()的不兼容函数,所以请使用功能测试宏。