在公共异常处理程序的catch块外部,不带参数的抛出语句

本文关键字:参数 语句 外部 异常处理程序 catch | 更新日期: 2023-09-27 17:50:13

我有一个常见的异常处理函数:

public static void ManageException(Exception ex,
                                   string customErrorMsg,
                                   bool displayMessage)

,我想从某些catch块中调用它。

处理完异常后,我想重新抛出异常,同时保留堆栈跟踪。

我在某处读到我应该不带任何参数的throw语句。throw语句(没有任何参数)在catch块中工作良好,但在我的ManageException函数中,它给了我一个编译错误:

在catch子句

之外不允许使用不带参数的throw语句

是否有任何解决方案重新抛出异常与整个堆栈跟踪和没有任何性能影响,从ManageException函数?

在公共异常处理程序的catch块外部,不带参数的抛出语句

如果确实需要在catch块之外重新抛出异常,可以使用以下方法:

ExceptionDispatchInfo.Capture(exception).Throw();

ExceptionDispatchInfo类从。net Framework 4.5开始可用。

通常,你不需要使用这个方法;相反,您可以a)在catch块中使用throw;命令重新抛出异常,或者b)将异常包装在另一个异常中。

必须指定要抛出的异常,如:

throw ex;

如错误中所述,您只能从catch块内部重新抛出异常(使用throw;)。恕我直言,这是唯一有意义的地方;您要么捕获异常,要么抛出异常,可能不应该两者都做。从一个名为ManageException的方法,我想知道为什么你会管理说异常,但无论如何抛出它。

也许您希望将原始异常包装在您自己的异常中,提供额外的细节?在这种情况下,我会抛出一个新的异常,ex作为InnerException,如果你想保留这些数据。


从你的评论,如果你想做的是确定你是否应该重新抛出一个异常,我建议:

  • 将您的方法重命名为TryManageException并更改签名以返回bool -如果异常管理不当并且需要重新抛出则返回false;如果被处理,返回true。
  • 如果方法返回false (= not managed),从catch块中重新抛出或执行其他需要的操作:

    try
    {
        decimal oops = 5 / 0;
    }
    catch (Exception e)
    {
        if (!CommonExceptionHandler.TryManageException(e, "oops", "oops"))
            throw;
    }
    

您的选择是:

。抛出catch块:

try
{
    //do stuff
}
catch (Exception ex)
{
    ManageException(ex);
    throw;
}

B。重新抛出处理程序方法:

private void ManageException(Exception ex)
{
    //log or whatever
    throw new Exception("See inner exception", ex);
}

C。更高级别的句柄:

例如在ASP中。. NET使用Global.asax中的Application_Error事件处理程序方法。
所有未处理的异常都结束并可以在那里处理。

只能从catch块内部重新抛出。想想吧;如果不在catch块中,则程序崩溃或在更高级别捕获异常。从catch块外部重新抛出是没有意义的。

将函数包装在try/catch中,并在需要时从catch中重新抛出。此外,如果你所做的一切都是重新投掷,那么就没有意义了;

你不能。

从MSDN

可以在catch块中使用throw语句来重新抛出被catch语句捕获的异常。

如果你想保留堆栈跟踪,你必须把它包装在InnerException

public static void ManageException(Exception ex, string customErrorMsg, bool displayMessage)
{
   ...
   throw new Exception ("Re-throwing", ex); // You can use your custom Exception object with custom message.
}

ManageException的调用者应该处理ex.InnerException而不是ex