问题
This is a behavior I noticed several times before and I would like to know the reason behind that. If you run the following program under the (Visual Studio 2008) debugger, the debugger will keep breaking on the throw
statement no matter how often you continue debugging. You have to stop debugging to get out there. I would expect that the debugger breaks once and then the process terminates as it happens if you run the program without the debugger. Is anybody aware of a good reason for this behavior?
using System;
namespace ExceptionTest
{
static internal class Program
{
static internal void Main()
{
try
{
throw new Exception();
}
catch (Exception exception)
{
Console.WriteLine(exception.Message);
// The debuger will never go beyond
// the throw statement and terminate
// the process. Why?
throw;
}
}
}
}
回答1:
Stepping over the unhandled exception would terminate the process - its probably just to stop you from accidentally terminating the process when you didnt intend to.
If the exception is handled elsewhere (such as in a generic outer try-catch block) then you will be able to step over the exception and the debugger will take you to the place where it is handled.
回答2:
If you want to kill the process, use the "Stop" button. There are times it's certainly useful to stop the application. The reason the debugger does not insist upon killing the application is that a programmer might want to examine the state of the program in the context of the thrown exception and/or "nudge" things in such a way that the program could continue. It's worthwhile to note that the debugger trap occurs before finalizers have run; this makes it possible to examine aspects of program state that would get destroyed during finalization.
Note also that it's possible to have an exception which will trigger the "uncaught exception" debugger trap and yet will not terminate the program. For example, one could do something like:
Class exTest Class myException Inherits Exception Sub New(ByVal innerException As Exception) MyBase.new("Wrapped Exception", innerException) End Sub End Class Shared Function CopyArg1ToArg2AndReturnFalse(Of T)(ByVal arg1 As T, ByRef arg2 As T) As Boolean arg2 = arg1 Return False End Function Shared Sub testIt() Dim theException As Exception = Nothing Try Try Throw New ApplicationException Catch ex As Exception When CopyArg1ToArg2AndReturnFalse(ex, theException) Throw Finally If theException IsNot Nothing Then Throw New myException(theException) End Try Catch ex As myException Debug.Print("Exception: " & ex.InnerException.ToString) End Try End Sub End Class
The system determines before any Finally clauses get triggered by the exception that nobody's going to capture ApplicationException. As it happens, though, if an exception does get thrown, the Finally clause will prevent that particular exception from escaping by throwing a new exception of its own--a new exception that will get caught.
This trick may be useful for debugging in situations where some exceptions will be trapped and handled at an inner level (without disrupting the user experience) while others will be trapped at an outer level (e.g. putting up an error message). The exceptions that will only be trapped at the outer level will generate a debugger trap when they occur, while those which are trapped at the inner level will allow the program to proceed.
回答3:
You cannot step past an exception that bubble all the way to the 'top' with out being handled Try this if you really need it:
static internal void Main()
{
try
{
throw new Exception();
}
catch (Exception exception)
{
Console.WriteLine(exception.Message);
// The debuger will never go beyond
// the throw statement and terminate
// the process. Why?
Environment.FailFast("Oops");
throw;
}
}
来源:https://stackoverflow.com/questions/1536954/why-does-an-unhandled-exception-not-terminate-a-process-while-debugging