为什么异常过滤器比捕获和重新抛出更可取?

Rol*_*ana 1 .net c# error-handling exception .net-4.6

基于这个问题(新Exception filter功能提供了哪些好处?).

该声明:

异常过滤器比捕获和重新抛出更可取,因为它们可以保持堆栈不受破坏.如果稍后的异常导致堆栈被转储,您可以看到它最初来自哪里,而不仅仅是它重新抛出的最后一个位置.

做一些测试后,我没有看到这两个之间的区别,新与旧,我还看到有人的地方例外重新抛出.所以,或者信息未被确认,我不理解异常过滤器(这就是我要问的原因),或者我做错了.你能解释一下为什么这个动作过滤器有优势吗?

class specialException : Exception
{
   public DateTime sentDateTime { get; } = DateTime.Now;
   public int code { get; } = 0;
   public string emailsToAlert { get; } = "email@domain.com";
}
Run Code Online (Sandbox Code Playgroud)

然后:

        try
        {
            throw new specialException(); //line 16
            throw new Exception("Weird exception");
            //int a = Int32.Parse("fail");
        }
        catch (specialException e) when(e.code == 0)
        {
            WriteLine("E.code 0");
            throw; // <-Line 23
        }
        catch (FormatException e) 
        {
                WriteLine("cond1 " + e.GetBaseException().Message+" "+e.StackTrace);
                throw;
        }
        catch (Exception e) //when (cond2)
        {
            Console.WriteLine("cond2! " + e.Message);
                throw;
        }
Run Code Online (Sandbox Code Playgroud)

结果:

在此输入图像描述

And*_*ndy 5

异常过滤的优点更多地与过滤器不匹配时有关,而不是在匹配时.如果删除catch除第一个块之外的所有块,并将第一个catch块上的过滤器更改为when(e.code != 0),则异常的callstack将指示它被抛出到第16行.

实现这一点的旧方法如下:

    try
    {
        throw new specialException(); //line 16
        throw new Exception("Weird exception");
        //int a = Int32.Parse("fail");
    }
    catch (specialException e)
    {
        if(e.code != 0)
        {
            WriteLine("E.code isn't 0");
            return;
        }

        throw;
    }
Run Code Online (Sandbox Code Playgroud)

在这种情况下,调用堆栈将指示在throw语句处抛出异常,而不是在第16行.