简体   繁体   English

捕获异常,添加数据并重新抛出它

[英]Catch Exception, add data, and rethrow it

I have the following code: 我有以下代码:

try
{
   OnInitialize();
}
catch (PageObjectLifecycleException exception)
{
   exception.OldLifecycleState = CurrentLifecycleState;
   exception.RequestedLifecycleState = LifecycleState.Initialized;
   throw exception;
}

I catch an exception, add some more data to it, and rethrow it. 我捕获一个异常,向它添加更多数据,然后重新抛出它。 Resharper warns me (correctly) that a rethrow is possibly intended and suggests changing it to: Resharper警告我(正确地)可能需要重新抛出并建议将其更改为:

throw;

But I'm wondering: Will this correctly rethrow the modified exception or the unmodified original one? 但我想知道:这是否正确地重新修改修改后的异常或未经修改的原始异常?

Edit : In response to the "Try it and see" comments: I am new to C#, comming from C++. 编辑 :回应“试一试”评论:我是C#的新手,来自C ++。 In C++ you often find undefined behaviour in corner cases like this and I am interested in whether what I want is really how it officially works. 在C ++中,你经常会在这样的极端情况下发现未定义的行为,我感兴趣的是我想要的是它是如何正式工作的。

You can add the extra information into data and re-throw the exception with throw so it maintains its original form and the callstack 您可以将额外信息添加到数据中并使用throw重新抛出异常,以便保持其原始形式和callstack

try
{
   ...
}
catch (PageObjectLifecycleException exception)
{
   exception.Data.Add("additional data", "the additional data");
   throw;
}

I know the answer's already been chosen but here's a little more info on the subject. 我知道已经选择了答案但是这里有关于这个主题的更多信息。

try {
    // code
}
catch(Exception e) {
    throw e;
}

The above code when compiled into IL will produce a call to throw passing a reference to the handled exception as an argument. 当编译成IL上面的代码将产生一个呼叫给throw传递一个参考处理的异常作为参数。 As you are probably aware, you can call throw from anywhere in your code to raise an exception. 您可能已经意识到,您可以从代码中的任何位置调用throw来引发异常。

try {
    // code
}
catch(Exception e) {
    throw;
}

The above code when compiled into IL will produce a call to rethrow . 编译成IL时上面的代码将产生一个rethrow的调用。 This is different to throw as rethrow is used to signal that the block in which the exception was handled has for some reason decided not to handle it and therefore, responsibility should be offered to a higher order catch block (next one up). 这是不同的,以throwrethrow来的信号,在该异常被处理该块出于某种原因决定不处理它,因此,责任应给予高阶catch块(下一个了)。

The rethrow method preserves the current call stack trace so that the origin of the exception can be tracked down. rethrow方法保留当前的调用堆栈跟踪,以便可以跟踪异常的来源。 However, the throw method starts a new call stack trace. 但是, throw方法启动一个新的调用堆栈跟踪。 I think this makes sense once you understand what the two methods are meant to be used for. 一旦你理解了两种方法的用途,我认为这是有道理的。

In my experience you use throw exception; 根据我的经验,你使用throw exception; when you want to throw an exception for some reason (eg validation of an object failed) and you would use throw; 当你想出于某种原因抛出异常时(例如对象的验证失败)你会使用throw; in a catch statement after you've performed some logging (ie while you still have access to useful information in the object that failed validation before passing exception handling responsibilities to a higher level). 在执行一些日志记录之后的catch语句中(即,在将异常处理职责传递到更高级别之前,您仍然可以访问验证失败的对象中的有用信息)。

In your example I would suggest that if you need to add more information to an exception you have a case for creating an entirely new exception and raising it. 在您的示例中,我建议如果您需要向异常添加更多信息,您可以创建一个全新的异常并提升它。 So you would use the throw exception; 所以你会使用throw exception; method where "exception" is a new exception containing the extra information and the originally thrown exception. 方法,其中“exception”是包含额外信息和最初抛出的异常的新异常。

Hope that helps! 希望有所帮助!

James 詹姆士

It will throw the reference to the modified exception. 它将抛出对修改后的异常的引用。

However I am not sure whether this is good programming style. 但是我不确定这是不是很好的编程风格。 Consider creating a new exception and add the PageObjectLifecycleException as its inner exception. 考虑创建一个新的异常并将PageObjectLifecycleException添加为其内部异常。 This way the handling code can be sure whether it has the correct additional information or not. 这样处理代码可以确定它是否具有正确的附加信息。

当前的异常被重新抛出,虽然我不确定你的模式是一个非常好的和可维护的模式。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM