如何在Visual Studio中忽略异步方法的特定异常INSTANCE(中断抛出)

时间:2017-01-06 07:47:10

标签: c# visual-studio exception async-await

如果我将VS设置为打破给定类型的抛出异常,并且调试器在某些代码中暂停,我会寻找继续运行(F5)和中断的可能性相同例外的父堆栈框架。

换句话说,我希望有可能忽略其堆栈框架其余部分的异常的实例(假设它被捕获到上面某处)。

我发现的唯一方法是乏味(如果在某些情况下经常抛出此类异常,则容易出错):取消选中"在抛出此类型时中断"复选框,继续执行,立即在“异常设置”窗格中重新激活该异常。

编辑:澄清第一个答案

我忘了提及(因为我不知道这是相关信息)我在异步方法中。我将您的示例修改为异步,如下所示:

    public static class Program
{
    public static void Main(string[] args)
    {
        try
        {
            Alpha();

        }
        catch (Exception e) // don't try this at home kids
        {
            // we should never get here in this example
            throw;
        }
    }


    private static async Task Alpha()
    {
        try
        {
            await Bravo(); //  *** 4 ***
        }
        catch (Exception e)
        {
            // debugger won't stop here because we didn't re-throw
        }
    }

    private static async Task Bravo()
    {
        try
        {
            await Tango(); //  *** 2 ***
        }
        catch (Exception)  // don't try this at home kids
        {
            throw;  // *** 3 *** debugger will stop here again because we are re-throwing
        }
    }

    private static async Task Tango()
    {
        var x = 1;
        var y = 0;
        var c = x / y; //  *** 1 ***

    }
}

调试器在编号顺序的所有四个标记点停止。所以它不仅停留在重新抛出,而且在所有等待中间停止。对于深度调用层次结构,这可能会令我的调试流程感到不安。

总而言之,我需要一个异步调用的解决方案,以便在导致异常的堆栈帧和最终捕获异常的堆栈帧之间的每次等待时都不会重新中断。

可能的?

1 个答案:

答案 0 :(得分:0)

随着问题中显而易见的新信息,这个答案可能不再合适。 :)

  

如果我将VS设置为打破给定类型的抛出异常,并且调试器在某段代码上挂起,我会寻找继续运行(F5)的可能性并且不会在同一异常的每个父堆栈帧上中断....

     

我发现的唯一方法是乏味(如果在某些情况下经常抛出此类异常,则容易出错):取消选中"在抛出此类型时中断"复选框,继续执行,立即重新激活“例外设置”窗格中的例外

如果没有看到您的代码,我只能假设您重新投掷相同的异常。

请考虑以下代码:

class Program
{
    static void Main(string[] args)
    {
        try
        {
            Alpha();

        }
        catch (Exception e) // don't try this at home kids
        {
            // we should never get here in this example
            throw;
        }

    }

    private static void Alpha()
    {
        try
        {
            Bravo();
        }
        catch (Exception e)
        {
            // debugger won't stop here because we didn't re-throw
        }
    }

    private static void Bravo()
    {
        try
        {
            Tango();
        }
        catch (Exception)  // don't try this at home kids
        {
            throw;  // debugger will stop here again because we are re-throwing
        }
    }

    private static void Tango()
    {
        var x = 1;
        var y = 0;
        var c = x / y;
    }
}

在抛出System.DivideByZeroException时将调试器设置为中断,调试器将:

  1. 先在Tango中停止尝试除以零并抛出第一个异常
  2. 再次停在catch() Bravo处理程序中,再次抛出异常
  3. 但它不会停留在Alpha,因为我默默地吃了这个例外。

    您所看到的行为是设计性的。