Bo *_*son 53
他们说他们不使用例外,而不是没有人应该使用它们.如果你看一下他们写的基本原理:
由于Google的大多数现有C++代码都没有准备好处理异常,因此采用生成异常的新代码相对比较困难.
通常的遗留问题.:-(
hof*_*anj 43
我们根本不处理容器引发的异常,至少在应用程序级代码中是这样.
自2008年以来,我一直是使用C++工作的Google搜索工程师.我们经常使用STL容器.我个人不记得曾经追溯到像vector :: push_back()或map :: operator []失败的单一主要故障或错误,我们说"哦,我们必须重写这段代码,因为分配可能失败"或"dang,如果我们只使用例外,这本来是可以避免的." 进程是否会耗尽内存?是的,但这通常是一个简单的错误(例如,有人向程序添加了一个大的新数据文件,忘了增加RAM分配)或者灾难性的失败,没有好的方法可以恢复和继续.我们的系统已经自动管理和重新启动作业,以便对具有故障磁盘,宇宙射线等的机器保持稳健,这实际上没有什么不同.
据我所知,这里没有问题.
我发现谷歌明确提到了STL和异常(重点是我的):
虽然您不应该在自己的代码中使用异常,但它们在ATL和一些STL中广泛使用,包括Visual C++附带的STL.使用ATL时,应定义_ATL_NO_EXCEPTIONS以禁用异常.您应该调查是否也可以在STL中禁用异常,但如果没有,则可以在编译器中打开异常.(注意,这只是为了让STL编译.你仍然不应该自己编写异常处理代码.)
我不喜欢这样的决定(幸运的是我不是为谷歌工作),但他们对自己的行为和意图非常清楚.
在现代操作系统上无论如何都无法处理分配失败; 作为性能优化,它们通常会过度提交内存.例如,如果你malloc()
在Linux上调用并要求一大块内存,那么即使实际支持它所需的内存不存在,它也会成功.只有当你访问它时,内核实际上才会尝试分配页面来支持它,那时告诉你分配失败已经太晚了.
所以:
除特殊情况外,不要担心分配失败.如果机器内存不足,那就是灾难性的故障,您无法可靠地恢复.
尽管如此,捕获未处理的异常并记录e.what()
输出然后重新进行是一种很好的做法throw
,因为这可能比回溯更具信息性,而典型的C++库实现并不会自动为您执行此操作.
关于如何在内存不足时不能依赖崩溃的全部大线程是完整的,完全是垃圾.C(++)标准可能无法保证,但在现代系统上,如果内存不足,崩溃是唯一可以依赖的事情.特别是,您不能依赖于NULL
从分配器获取或实际上任何其他指示,直到并包含C++异常.
如果您发现自己位于可访问页面零的嵌入式系统上,我强烈建议您通过在该位置映射无法访问的页面来解决此问题.人类不能依靠其检查NULL
到处指针,但你可以通过映射页面修复一次,而不是试图纠正每一个可能的(过去,现在和将来)在这有人可能会错过一个位置NULL
.
我将通过说你可能正在使用某种自定义分配器,或者你所处的系统没有过度提交(没有交换的嵌入式系统就是一个例子,但不是唯一的例子)来限定上述内容.例).在这种情况下,也许您可以在系统上优雅地处理内存不足的情况.但总的来说,在21世纪,我担心你不太可能有机会; 第一个你会知道你的系统内存不足就是事情开始崩溃的时候.
小智 5
Stl本身仅在内存分配失败的情况下直接抛出。但通常现实世界的应用程序可能会因多种原因而失败,内存分配失败只是其中之一。在 32 位系统上,内存分配失败不应该被忽略,因为它可能会发生。因此,上面关于内存分配失败不会发生的整个讨论是毫无意义的。即使假设这一点,人们也必须使用两步初始化来编写代码。C++ 异常处理早于 64 位架构出现很长时间。我不确定我应该在多大程度上尊重谷歌在这里显示的负面专业精神,并且只回答所提出的问题。我记得 1997 年左右 IBM 发表的一篇论文阐述了 IBM 的一些人如何很好地理解和欣赏 C++ 异常处理的含义。好吧,专业精神并不一定是成功的指标。因此,放弃异常处理不仅是使用 STL 的问题。如果像这样使用 C++,那就是一个问题。意味着放弃
归档时间: |
|
查看次数: |
20091 次 |
最近记录: |