从应用程序代码抛出OutOfMemoryException是好的设计

本文关键字:OutOfMemoryException 应用程序 代码 | 更新日期: 2023-09-27 18:14:56

我记得我在某处读到过,从用户代码中抛出任何System.SystemException派生的异常是一种不好的做法,因为用户代码应该只抛出应用程序异常。

我们有一个使用GPU的本地库。它可能会返回一个错误代码,表明我们的GPU内存不足。我们想把这个错误代码转换成。net异常。

这是我能想到的可能的例外:

  1. System.OutOfMemoryException
  2. System.InvalidOperationException与适当的文字
  3. 自定义异常(基于InvalidOperationException)

哪一个是最好的,为什么?

从应用程序代码抛出OutOfMemoryException是好的设计

System.OutOfMemoryException不是理想的选择。使用您的库的程序员可能会对System.OutOfMemoryException做出反应,从内存中清除一些不重要的对象,然后再次尝试。然而,在你的情况下,它是GPU内存,而不是系统内存,所以他们的尝试将没有机会工作。

如果用户可以选择直接或间接地从GPU内存中卸载东西,自定义异常方法(第三条)提供了最干净的选择。如果他们完全无法控制它,即异常基本上是一个"你死了"的消息,那么System.InvalidOperationException也是一个不错的选择。

引发OutOfMemoryException是最糟糕的选择。这样做的原因是,这种异常在一般情况下几乎不可能恢复,对于客户端来说,很难确定是系统内存耗尽还是您只是滥用了这种异常类型,特别是因为客户端不会期望这种行为。

引发InvalidOperationException是一件更好的事情,因为客户端将能够处理这个问题(通过将计算卸载到其他地方或在CPU中执行所需的东西,可能使用不同的库)。但是,如果异常是InvalidOperationException,则该异常类型很可能也被其他库或BCL使用。因此,客户端必须通过解析错误消息来响应此异常,这是不可靠的。

因此,最好的解决方案是自定义异常类型,因为这将使客户端能够捕获该异常类型并从这种情况中恢复,或者告诉用户问题所在。您是否认为这是一个无效操作的特殊情况取决于您。就个人而言,我不会让异常从InvalidOperationException继承,而是直接从Exception继承。

抛出的异常应该具有信息性,因此让我们查找候选异常:

System.OutOfMemoryException

https://msdn.microsoft.com/en-us/library/system.outofmemoryexception (v = vs.110) . aspx

OutOfMemoryException异常有两个主要原因:

  • 你正在尝试扩展StringBuilder对象,超出其StringBuilder定义的长度。MaxCapacity财产。
  • 公共语言运行库无法分配足够的连续内存来成功执行操作。这个例外可以是的任何属性赋值或方法调用都会抛出内存分配。有关事故原因的更多信息OutOfMemoryException异常,参见"Out of Memory"不参考物理内存。

读过这篇文章后,我认为System.OutOfMemoryException是一个非常错误的候选人:它误导了,因为在你的情况下问题是与GPU而不是与RAM

第二个候选者是

System.InvalidOperationException

https://msdn.microsoft.com/en-us/library/system.invalidoperationexception (v = vs.110) . aspx

方法调用无效时引发的异常对象的当前状态

小姐;状态为OK,是GPU内存不足。

所以我建议实现你自己的自定义异常,然而,不基于System.InvalidOperationException,而是基于Exception通过抽象GpuException:

   Exception
     GpuException               // Abstract (wrong GPU, lack of support etc.)
       GpuOutOfMemoryException  // Not enough memory on board 
相关文章:
  • 没有找到相关文章