Try-Catch没法正肯定位异常位置,我推荐2个有效技巧

宇宙第一开发IDE Visual Studio的调试功能很是强大,日常工做debug帮助咱们解决很多问题。今天分享两个异常捕获的技巧,但愿可以帮助解决一些问题。
如下两种状况,我相信你们都会遇到过。程序员

  • 1.没有使用Try-Catch语句,当异常发生的时候,可以自动跳转到异常发生的地方,在使用Try-Catch捕获异常的时候,直接跳转到Catch语句的位置,并不会自动定位到异常代码的位置。
  • 2.使用Try-Catch的时候,多层方法调用时,并不能直接查看到异常代码的位置。

技巧1:自动定位到异常代码位置

针对问题1,咱们最想要的结果是,哪里有代码出现错误了,就直接定位到哪儿,异常出在哪行代码上,我一眼就能看得出,这样就能更快地处理问题了。
对于问题1,所出现的这种状况,简单复现一下一个空引用的异常dom

namespace ExceptionSample
{
    class Program
    {
        static void Main(string[] args)
        {
            try
            {
                Random random = null;
                Console.WriteLine(random.Next());
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex);
            }
            Console.ReadLine();
        }
     }
}

上面的异常代码NullReferrenceException,Debug模式下,会跳转到catch语句这里。你可能以为这挺简单的......可实际实际工做中,你的一个方法中仅仅只这一个对象吗?
在这里插入图片描述
在实际工做中可能不止random一个对象,代码复杂,对象够多,几十个也有,咱们就很难定位到异常出错的代码了。StackTrace能够定位到那个函数调用错了,并不能定位到哪一行代码出错了。
为了解决这个行为能够经过在Visual Studio中菜单栏中的调试》窗口》异常设置中去配置。以下图所示:
在这里插入图片描述
勾选上Common Language Runtime Exceptions下列的异常单选框。有点多,之前的设置有些变化。
如今咱们再看以前的代码,使用Try-Catch语句捕获异常的时候,就会直接定位到异常代码的位置了,以下图示:函数

static void Main(string[] args)
        {
            try
            {
                Random random = null;
                Random random1 = new Random();
                Random random2 = new Random();
                Random random3 = new Random();
                Console.WriteLine(random1.Next());
                Console.WriteLine(random2.Next());
                Console.WriteLine(random3.Next());
                Console.WriteLine(random.Next());
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex);
            }
            Console.ReadLine();
        }

在这里插入图片描述

技巧2:正常的throw 姿式

仍是以前的一个方法,我已经将异常设置回复默认了。spa

static void Main(string[] args)
        {
            try
            {
                Random random = null;
                Console.WriteLine(random.Next());
            }
            catch (Exception ex)
            {
                System.Diagnostics.Debug.Write(ex);
                throw ex;
            }
        }

咱们再输出中能够看到(ps:项目名称用的以前的,不介意哈)
在这里插入图片描述
错误的代码在16行。可实际工做中的状况并非这样简单,基本上是A方法调用B方法,B方法调用C方法,代码以下所示:
在Main方法中调用ThrowNullReferrence(),方法ThrowNullReferrence中调用SetNullReferrence()。代码变复杂后,一层嵌套一层。这个时候能正确显示出代码异常的位置吗?debug

static void Main(string[] args)
        {
            try
            {
                ThrowNullReferrence();
            }
            catch (Exception ex)
            {
                System.Diagnostics.Debug.Write(ex);
                throw ex;
            }
        }
        public  static void ThrowNullReferrence()
        {
            try
            {
                SetNullReferrence();
            }
            catch (Exception ex)
            {
                System.Diagnostics.Debug.Write(ex);
                throw ex;
            }
        }
        public static void SetNullReferrence()
        {
            try {
                Random random = null;
                Console.WriteLine(random.Next());
            }
            catch(Exception ex)
            {
                System.Diagnostics.Debug.Write(ex);
                throw ex;
            }
        }

咱们能够经过下图看到:
在这里插入图片描述
System.NullReferenceException: 未将对象引用设置到对象的实例。
在 ExceptionSample.Program.SetNullReferrence() 位置 D:\Learn\延迟加载\LinqLayzLoad\LinqLayzLoad\Program.cs:行号 39System.NullReferenceException: 未将对象引用设置到对象的实例。
在 ExceptionSample.Program.SetNullReferrence() 位置 D:\Learn\延迟加载\LinqLayzLoad\LinqLayzLoad\Program.cs:行号 44
在 ExceptionSample.Program.ThrowNullReferrence() 位置 D:\Learn\延迟加载\LinqLayzLoad\LinqLayzLoad\Program.cs:行号 27System.NullReferenceException: 未将对象引用设置到对象的实例。
在 ExceptionSample.Program.ThrowNullReferrence() 位置 D:\Learn\延迟加载\LinqLayzLoad\LinqLayzLoad\Program.cs:行号 32
在 ExceptionSample.Program.Main(String[] args) 位置 D:\Learn\延迟加载\LinqLayzLoad\LinqLayzLoad\Program.cs:行号 153d

错误代码的位置在39行,以上出现异常的地方都是throw的位置。
缘由呢?
catch捕获完后,若是要向上抛出,应该从新实例化一个新的异常对象,再向上抛出,这个最外层方法catch到的才是完整的异常,固然也包括完整的堆栈信息,这样才能定位到异常代码的位置。
要使用 throw new Exception
改造后的例子如图,精准定位到
39行的空引用异常
Console.WriteLine(random.Next());
在这里插入图片描述调试

结语

分享以前看到的一个老程序员的经验之谈:“多coding,少debug”code

相关文章
相关标签/搜索