例外与错误
Exceptions vs. errno
作为一名C程序员,我对异常没有太多经验。我习惯于errno
作为在多个函数调用之间传达错误的一种方式。话虽如此,我没有看到例外的显着特征,所以......
例外和使用errno
的根本区别是什么?
这里有很多差异,很难说从哪里开始。
首先,C 中使用的errno
是一个全局变量;这意味着每个调用 errno
-set 子例程的例程都必须在执行任何其他工作之前检查errno
,如果它关心正确性。幸运的是,errno 是线程安全的。
C++异常会自动展开调用堆栈,直到找到准备好处理错误的函数。这意味着在大多数情况下,用户不必显式检查每个调用是否存在错误;相反,他们可以在一个地方收集错误返回。C++异常可以包含整数以外的值,这与 errno 不同。
你可以随便忽略errno。 必须处理例外情况。
当然,我已经看到了我的份额:
try {
// something
}
catch( ... ) {
// nothing
}
// continue as if nothing happened
和(爪哇)
try {
// something
}
catch( Throwable t ) {
// nothing
}
// continue as if nothing happened
但至少当你在别人的烂摊子里耕耘时,这种感觉会跳出来。
有必要指出,面对异常编写正确的程序并不容易。 你最好对这个主题做一些研究,也许从本周大师开始。 只需寻找exception
这个词.
1)异常可以是任何东西,而不仅仅是整数。因此,传达的数据是不同的。
2) 异常执行非本地控制流,因此您不必像在实践中使用 errno
那样在每个级别进行检查,您还返回一个指示错误的值,并且每个调用方都会检查错误并在发生错误时尽早救援。相反,错误返回执行本地控制流,因此您始终可以准确地看到错误何时通过给定代码段传播。这种差异从根本上改变了编码风格。所以沟通的方式也不同。
,最重要的区别是errno
很容易被忽略,而异常很难被忽视 - 如果你最终忽略它们,程序将终止......另外,异常是(嗯,应该是)对象,因此您可以携带更多有用的信息。
另一个非常重要的区别是,在软件实际上可以做出如何处理问题的明智决策时,可以很容易地处理异常,这通常是调用堆栈的几个级别。使用错误代码并不容易做到。
我发现在嵌入式系统上有用的一种模式是为每个流设置一个错误标志,但前提是在设置标志时尝试的 I/O 操作将立即失败。 因此,代码可以执行以下操作:
pkt_type = tcp_getbyte(my_stream,超时); pkt_length = tcp_getbyte(my_stream,超时); pkt_length |= tcp_getbyte(my_stream,超时) <<8; 如果 (pkt_length <MAX_PACKET_LENGTH)>错误) { /* 对数据包做点什么 */ }
如果一次尝试获取字节超时,则后续尝试将无条件失败,返回零。 没有必要检查每个操作是否失败;如果出现问题,系统最终的行为将大致像 tcp_getbyte() 抛出异常一样,只是没有那么快。
- 警告处理为错误这里有什么问题
- "error: no matching function for call to"构造函数错误
- boost::进程间消息队列引发错误
- C++,OpenCV,尝试显示图像时"OpenCV(4.3.0) Error: Assertion failed (size.width>0 && size.height>0)"此错误
- 有关插入适配器的错误。[错误]请求从 'back_insert_iterator<vector<>>' 类型转换为非标量类型
- QT在错误的班级中寻找空位
- vector.resize()中的分配错误
- 代码在main()中运行,但在函数中出现错误
- 释放错误后堆使用
- (C++)分析树以计算返回错误值的简单算术表达式
- Project Euler问题4的错误解决方案
- 我的字符计数代码计算错误.为什么
- 从"int*"强制转换为"unsigned int"会丢失精度错误
- 尝试导入pybind-opencv模块时出现libgtk错误
- CMake项目Boost库错误:Boost/config/compiler/gcc.hpp:165:10:致命错误:cs
- 在某些循环内使用vector.push_back时出现分段错误
- MSVC多行宏编译器错误
- 静态数据成员的问题-修复链接错误会导致编译器错误
- 为什么在运行时没有向我们提供有关分段错误的更多信息?
- 错误:未在此范围内声明'reverse'