Som*_*mer 3 c++ undefined-behavior
C++ 中的未定义行为真的很难调试。是否有一个版本的 C++ 和标准库不包含任何未定义的行为而是抛出异常?我知道这将是一个性能杀手,但我只打算在我在调试模式下编程、调试和编译时使用这个版本,并不真正关心性能。理想情况下,此版本是可移植的,您可以轻松打开/关闭未定义的行为检查。
例如,你可以实现一个像这样的安全指针类(只检查空指针,实际上如果它指向一个有效的内存块,则不会):
template <typename T>
class MySafePointer {
T* value;
public:
auto operator-> () {
#ifndef DEBUG_MODE
assert(value && "Trying to dereference a null pointer");
#endif
return value;
}
/* Other Stuff*/
};
Run Code Online (Sandbox Code Playgroud)
在这里,用户只需要#undef DEBUG_MODE在您想恢复性能时才需要。
是否有 C++ 的库/安全版本可以做到这一点?
编辑:更改了上面的代码,使其实际上更有意义并且不会抛出异常但断言值非空。问题只是一个描述性错误消息与崩溃的问题......
是否有一个版本的 C++ 和标准库不包含任何未定义的行为而是抛出异常?
不,那里没有。正如评论中提到的,有 Address Sanitizer 和 Undefined Behavior Sanitizer 以及许多其他可以用来寻找错误的工具,但没有“没有未定义行为的 C++”实现。
如果您想要一种本质安全的语言,请选择一种。C++ 不是。
未定义的行为意味着您的程序最终处于标准未定义其行为的状态。\xc2\xb9
\n所以你真正要问的是是否有一种语言的标准定义了所有可能的场景。
\n我想不出一种这样的语言,原因很简单,程序是由机器运行的,而编程语言和标准是由人类编写的。
\n根据上述原因,该标准可能存在无意的“漏洞”,即未有意允许的未定义行为,甚至可能在标准化过程中没有注意到。
\n然而,正如标准中所有“未定义行为”句子所证明的那样,很多时候 UB 是被有意允许的。
\n但为什么?因为这意味着给程序员提供更少的保证,而好处是能够进行更多优化,或者等效地,不浪费时间验证用户是否遵守定义的合同。
\n因此,即使标准没有漏洞,标准中仍然会出现很多情况,因为编译器可以利用它来进行各种优化。\xc2\xb2
\nstd::vector未定义行为的一个小例子是当您访问via的越界元素时operator[]。与 C 风格数组完全相同,v[i]基本上返回*(v_ + i),v_包装到 中的指针在哪里v。这很快但不安全。\xc2\xb3
如果你想i安全地访问第 th 元素怎么办?您将不得不更改的实现std::vector<>::operator[]。
那么支持国旗会产生什么影响呢DEBUG_MODE?本质上,您必须编写两个实现,并用#ifdef/( #else/)分隔#endif。显然,这两种实现有很多共同点,因此您可以#在代码中进行多次分支。但是......是的,我的底线是可以通过改变标准来满足您的要求,从而迫使实施者为所有事情支持两种不同的实现(安全和快速/不安全和慢速)。
顺便说一句,对于这种特定情况,标准确实定义了另一个函数 ,at它需要处理越界情况。但这就是重点:它是另一个函数。
(\xc2\xb9) 在这种情况下标准(我的重点)
\n\n\n对使用该输入执行该程序的实现没有任何要求(甚至对于第一个未定义操作之前的操作也没有要求)
\n
(\xc2\xb2) 我真的建议阅读Nicol Bolas的这个关于 s 中缺少 UB 的答案。constexpr
(\xc2\xb3)这篇优秀的文章中列出了 UB 的这个例子和其他例子;搜索Out of Bounds以获取我制作的示例。
\n| 归档时间: |
|
| 查看次数: |
192 次 |
| 最近记录: |