C#异常处理 — try、catch语句

 

一、为异常寻找处理程序

首先先放一张处理异常的一般法则图片,这是异常发生后系统寻找异常处理程序规则的流程:

该图片摘抄自 Solis, D.M., Illustrated C# 2012(Fourth Edition). 2013: 人民邮电出版社. 

 

以下代码是个人用来学习记录,功能是看懂try、catch语句可以看懂在搜索调用栈来寻找一个异常处理程序的顺序。

/*  
 *  时间:2019年1月23日15点34分
 *  功能:看懂搜索try\catch语句搜索调用栈寻找一个异常处理程序的顺序
 */

using System;

/// <summary>
/// 包含两个方法的类型,其中B类型是异常的
/// </summary>
class MyClass
{
    public void A()
    {
        try
        {
            B();
        }
        catch (NullReferenceException)
        {
            Console.WriteLine("catch clause in A()");
        }
        finally
        {
            Console.WriteLine("finally clause in A()");
        }
    }

    public void B()
    {
        int x = 10, y = 0;

        try
        {
            x /= y;     //异常,异常类型:DivideByZeroException
        }
        catch (IndexOutOfRangeException)
        {
            Console.WriteLine("catch clause in B()");
        }
        finally
        {
            Console.WriteLine("finally clause in B()");
        }
    }
}



/// <summary>
/// 主程序
/// </summary>
class Program
{
    static void Main()
    {
        MyClass myClass = new MyClass();

        try
        {
            myClass.A();
        }
        catch (DivideByZeroException)
        {
            Console.WriteLine("catch clause in Main()");
        }
        finally
        {
            Console.WriteLine("finally clause in Main()");
        }

        Console.WriteLine("After try statement in Main()");
        Console.WriteLine(" --------------- Keep Running");

        Console.ReadKey();
    }
}



/* 程序运行结果
-----------------------------------------
    finally clause in B()
    finally clause in A()
    catch clause in Main()
    finally clause in Main()
    After try statement in Main()
     --------------- Keep Running
-----------------------------------------
 */

二、异常抛出

可以使用throw语句显式地引发一个异常,下面的代码定义了一个名称为PrintArg()的方法,它带一个string参数并打印出来。在try块的内部,首先做检查以确定该参数不是null。如果是null,它创建一个ArgumentNullException实例并抛出它。该异常在catch语句中捕获,并且该出错消息被打印。Main调用该方法两次:一次用null参数,一次用一个有效参数。

/*  
 *  时间:2019年1月23日15点57分
 *  功能:抛出异常
 */

using System;

/// <summary>
/// 抛出异常
/// </summary>
class MyClass
{
    public static void PrintArg(string Arg)
    {
        try
        {
            if (null == Arg)
            {
                ArgumentNullException myEx = new ArgumentNullException("Arg");
                throw myEx;
            }
            Console.WriteLine(Arg);
        }
        catch(ArgumentNullException e)
        {
            Console.WriteLine("Message: {0}",e.Message);
        }
    }
}



/// <summary>
/// 主程序
/// </summary>
class Program
{
    static void Main()
    {
        string s = null;
        MyClass.PrintArg(s);

        MyClass.PrintArg("Hello!");       

        Console.ReadKey();
    }
}


/* 程序运行结果
 --------------------------------------------
  Message: Value cannot be null.
  Parameter name: Arg
  Hello!
 --------------------------------------------
 */

为什么这里需要写程序时主动让它参数为null就抛出异常?

因为类似于这样的例子,参数为null程序运行时候系统并不认为这是一个异常,但是会对结果产生很大的影响。而我们写程序的时候控制让它参数为空就抛出异常,这样可以尽最大可能保证程序运行时候的稳定性,归根结底还是让程序不能自动识别异常的时候手动抛出。

 

三、不带异常对象的抛出

throw语句还可以不带异常对象使用,在catch语句块内部。

1、这种形式重新抛出当前异常,系统继续它的搜索,为该异常寻找另外的处理代码

2、这种形式只能用在catch语句内部

/*  
 *  时间:2019年1月23日16点10分
 *  功能:不带异常对象的抛出
 */

using System;

/// <summary>
/// 抛出异常
/// </summary>
class MyClass
{
    public static void PrintArg(string Arg)
    {
        try
        {
            try
            {
                if (null == Arg)
                {
                    ArgumentNullException myEx = new ArgumentNullException("Arg");  //提供null参数的名称
                    throw myEx;
                }
                Console.WriteLine(Arg);
            }
            catch (ArgumentNullException e)
            {
                Console.WriteLine("Inner Catch: {0}",e.Message);
                throw;  //重新抛出异常,没有附带参数
            }
        }
        catch
        {
            Console.WriteLine("Other catch: Handing an Exception.");
        }
    }
}



/// <summary>
/// 主程序
/// </summary>
class Program
{
    static void Main()
    {
        string s = null;
        MyClass.PrintArg(s);      

        Console.ReadKey();
    }
}

/* 程序运行结果
 --------------------------------------------
    Inner Catch: Value cannot be null.
    Parameter name: Arg
    Other catch: Handing an Exception.
 --------------------------------------------
 */

 

 

  • 1
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值