我一直在阅读所有地方(包括这里)关于何时应该/不应该使用异常。 我现在想要改变我的代码,它会抛出使方法返回false并像这样处理它,但我的问题是:它是抛出还是尝试......它会阻碍性能......? 我的意思是,这是否可以接受:
bool method someMmethod()
{
try
{
// ...Do something
catch (Exception ex) // Don't care too much what at the moment...
{
// Output error
// Return false
}
return true // No errors
或者有更好的方法吗? (我很害羞地看到“未处理的异常......”哈哈!)
答案 0 :(得分:6)
问自己以下问题:异常例外吗?
答案 1 :(得分:4)
如果您的问题是try...catch
阻止是否会影响效果,则不会。
如果你的问题是使用基于异常的模型而不是返回值模型是否有性能损失,那么是的,有。有这样的功能:
public void DoWork()
{
if(something) throw new Exception(...);
}
在错误条件下不会像这样的函数表现得那么好:
public bool DoWork()
{
if(something) return false;
return true;
}
异常必须展开堆栈并将你踢出最近的catch
块以便工作,因此会产生开销。返回一个状态值更简单,但是当异常不是规则时,它也是一个更加不连贯的界面。
但是,这不是重点。如果您正在编写代码,而异常是规则,那么您就遇到了问题。例外情况应该用于......例外情况,例如当您遇到无法在代码中解释的情况时。
考虑int
和DateTime
等类型。这些类型提供(以及其他)两个不同的函数,用于将字符串值转换为相应的int
和DateTime
值:Parse
和TryParse
。 Parse
使用异常模型,因为它假设你将传递一个结构良好的整数值,所以如果它得到 else ,那就是一个例外情况。另一方面,TryParse
是专门为您不确定字符串的格式而设计的,因此它使用返回值模型(以及out
参数以获得实际转换值)。
答案 2 :(得分:2)
例外情况适用于特殊情况。如果您的// ...Do something
在正常流程中抛出异常,请进行修复。
答案 3 :(得分:2)
如果你有一个try / catch块并且这个块没有抛出异常,它的运行速度就像没有try / catch块包装它一样。只有在实际抛出异常时,性能才会下降,但如果您按设计使用异常,则无关紧要,因为您现在处于异常情况。不应将例外用于控制流程。
答案 4 :(得分:1)
试一试......抓住代码并不会真正阻碍性能,可能失败的代码应该总是试一试......抓住它。
但是,您应该始终避免首先抛出异常,因为这些异常会影响性能。
Never throw an exception unless it is truly exceptional!
您的返回false表示与TryParse()
方法类似的模式。
答案 5 :(得分:1)
它只是你不应该允许异常为逻辑引发,即你不应该让catch块负责或总是返回false。简单地说,它不应该用于逻辑。
例如,当你可以检查null并返回false时,你不应该调用null上的方法来获得NullReferenceException并让catch块返回false。
答案 6 :(得分:1)
开发人员认为捕获异常是一个常见的误解,这是一个好主意。
如果异常恰好是StackOverflowException或OutOfMemoryException,那么你可能就是这样 不希望你的申请在这些情况下继续。
关于性能,使用异常来控制程序流会严重影响性能,部分原因是每次抛出异常时clr必须遍历堆栈以找到catch语句(称为堆栈展开)
TryXXX模式是尝试执行某些操作而不会抛出异常的一种方法。
答案 7 :(得分:0)
在性能方面,你不会看到任何差异。这是一种微观优化,因为它阻碍了性能的发展。
然而......那就是说,我不相信你这样做的动机是完全有效的。如果抛出的函数是你自己的函数,那么我猜它抛出一个原因并且捕获异常可能会隐藏一个重要的错误。
答案 8 :(得分:0)
我经常听说第一次抛出时异常很慢,因为某些模块或任何必须加载的东西。但是,正如Blorgbeard所说,例外是针对例外情况。没关系。