VB.net 2010 视频教程 VB.net 2010 视频教程 c#入门经典教程
当前位置:
主页 > 编程开发 > c#教程 >
  • c#教程之c#异常处理

  • 2016-02-20 14:35 来源:未知
c#异常处理
 
什么是异常?
    异常是程序执行时遇到的任何错误情况或意外行为。
 
异常类和属性
     Exception 类是异常从其进行继承的基类。大多数异常对象都是 Exception 的某个派生类的实例,不过,任何从Object 类派生的对象都可以作为异常引发。
 
Exception 类的若干属性使了解异常更容易。这些属性包括:
1、StackTrace 属性。
此属性包含可用来确定错误发生位置的堆栈跟踪。如果有可用的调试信息,则堆栈跟踪包含源文件名和程序行号。
2、InnerException 属性。
     此属性可用来在异常处理过程中创建和保留一系列异常。可使用此属性创建一个新异常来包含以前捕捉的异常。原始异常可由 InnerException 属性中的第二个异常捕获,这使处理第二个异常的代码可以检查附加信息。
     例如,假设有一个读取文件并格式化相应数据的方法。代码试图从文件读取,但引发 FileException。该方法捕捉 FileException 并引发 BadFormatException。在此情况下,FileException 可保存在 BadFormatException 的 InnerException 属性中。
    为提高调用方确定异常引发原因的能力,有时可能需要方法捕捉帮助器例程引发的异常,然后引发一个进一步指示已发生的错误的异常。可以创建一个更有意义的新异常,其中内部异常引用可以设置为原始异常。然后可以针对调用方引发这种更有意义的异常。请注意,使用此功能,可以创建以最先引发的异常作为结束点的一系列相链接的异常。
3、Message 属性。
     此属性提供有关异常起因的详细信息。Message 用引发异常的线程的 Thread.CurrentUICulture 属性所指定的语言表示。
4、HelpLink 属性。
此属性可保存某个帮助文件的 URL(或 URN),该文件提供有关异常起因的大量信息。
5、Data 属性
此属性是可以保存任意数据(以键值对的形式)的 IDictionary。
 
大多数从 Exception 继承的类都不实现其他成员或提供附加功能;它们只是从 Exception 继承。因此,在异常层次结构、异常名称以及异常包含的信息中可以找到有关异常的最重要信息。
 
 
c#异常处理所用到的几个关键字:
1、try 用于检查发生的异常,并帮助发送任何可能的异常。
2、catch 以控制权更大的方式处理错误,可以有多个catch子句。
3、finally 无论是否引发了异常,finally的代码块都将被执行。
4、throw 用于引发异常,可引发预定义异常和自定义异常。
 
try
{
 
    程序代码块;
 
}
 
catch(Exception e)
 
{
 
    异常处理代码块;
 
}
 
finally
 
{
 
    无论是否发生异常,均要执行的代码块;
 
}
 
下面看一个简单的例子:
 
//int y = 0;
 
try
 
{
 
         int z = x / y;
 
}
 
catch (DivideByZeroException ex)
 
{
 
       Response.Write("除数不能为0,你知道吗?" + ex.Message);
 
}
catch(…..  e)
 
{
 
    异常处理代码块;
 
}
catch(Exception e)
 
{
 
    异常处理代码块;
 
}
 
finally
 
{
 
        Response.Write("无论是否有异常,我都会出现");
 
}
 
运行的输出结果是:
 
 
2、每个try语句必须有一个或多个catch语句对应,try代码块与catch代码块以及finally代码块之间不能有其他语句。下面的语句是错误的:
try
 
{
 
}
 
catch (DivideByZeroException ex)
 
{
 
    ......
 
}
 
    x = 8;//放在这里是不行滴
 
finally
 
{
 
  .....
 
}
 
可以给try语句提供多个catch语句,以捕获特定的异常,如上例中:0作为除数则会引发DivideByZeroException类型的异常,上例中的catch语句可以作如下修改:
catch (DivideByZeroException ex)
 
{
 
       Response.Write("除数不能为0,你知道吗?" + ex.Message);
 
}
 
catch(Exception e)
 
{
 
          Response.Write("其它异常\"!异常值为:" + e.message);
 
}
 
 
为什么还要加上一个catch(Exception e)子句呢?原因很简单,catch (DivideByZeroException ex)子句只能捕获特定的异常,try内的程序代码可能还会产生其它的异常,这些异常只能由catch(Exception e)来捕获了。
 
ArgumentException 参数错误:方法的参数无效
 
ArgumentNullException 参数为空:给方法传递一个不可接受的空参数
 
ArithmeticException 数学计算错误:由于数学运算导致的异常,覆盖面广。
 
ArrayTypeMismatchException 数组类型不匹配
 
DivideByZeroException 被零除
 
FormatException 参数的格式不正确
 
IndexOutOfRangeException 索引超出范围,小于0或比最后一个元素的索引还大
 
InvalidCastException 非法强制转换,在显式转换失败时引发
 
MulticastNotSupportedException 不支持的组播:组合两个非空委派失败时引发
 
NotSupportedException 调用的方法在类中没有实现
 
NullReferenceException 引用空引用对象时引发
 
OutOfMemoryException 无法为新语句分配内存时引发,内存不足
 
OverflowException 溢出
 
StackOverflowException 栈溢出
 
TypeInitializationException 错误的初始化类型:静态构造函数有问题时引发
 
NotFiniteNumberException 无限大的值:数字不合法
 
除了系统提供的异常,我们也可以定义自己的异常类,该类必须继承于Exception,下面举个简单例子:
 
 
 
using System;
 
using System.Data;
 
using System.Configuration;
 
using System.Collections;
 
using System.Web;
 
using System.Web.Security;
 
using System.Web.UI;
 
using System.Web.UI.WebControls;
 
using System.Web.UI.WebControls.WebParts;
 
using System.Web.UI.HtmlControls;
 
using System.IO;
 
public partial class Default2 : System.Web.UI.Page
 
{
 
    protected void Page_Load(object sender, EventArgs e)
 
    {
 
        int num = 1;
 
        try
 
        {
 
            if (num > 0)
 
            {
 
                throw new myException();
 
            }   
 
        }
 
        catch (myException ex1)
 
        {
 
            Response.Write(ex1.Message);
 
        }
 
        catch (Exception ex2)
 
        {
 
            Response.Write("如果第一个catch过了,还得过我这一关,出现的错误原因是:" + ex2.Message);
 
        }
 
        finally
 
        {
 
            Response.Write("");
 
        }
 
    }
 
    //重写Exception的Message
 
    protected class myException:Exception
 
    {
 
        public override string  Message
 
        {
 
           get
 
           {
 
                   return "大于0,你不知道吗?";
 
           }  
 
         }
 
    }
 
}
 
 
上面的例子重写了Execpton中的Message属性。
 
1、一个方法被覆盖时,覆盖它的方法必须抛出相同的异常或异常的子类。
 
2、如果父类抛出多个异常,那么重写(覆盖)方法必须抛出那些异常的一个子集,也就是说,不能抛出新的异常。
 
       以前语言要求程序员使用函数调用的返回值来判断执行情况,这种方式有很多缺陷,因为对许多可能出现的异常情况需要不同程度的了解。有些语言使用一个全局变量来保存异常状态,但这种方式是远远不够的,因为后面的异常会在前一个异常还未处理之前就覆盖了那个全局变量的值。
 
 
【实例题目】
编写一个控制台程序,程序名为divpro,程序的功能是求两个整数的商。要求程序运行情况如下:
(1)如果以命令行“divpro 10 5”的形式运行,将出现正常结果,显示“10 除 5的商为:2”
(2)如果以命令行“divpro”、“divpro 10” 的形式运行,将出现提示信息:“输入参数不够”
(3)如果以命令行“divpro abcd”或“divpro 10 asdhjk”的形式运行,将出现提示信息:“输入字符串的格式不正确”
(4)如果以命令行“divpro 10 0”的形式运行,将出现提示信息:“试图除以零”
(5)如果以命令行“divpro 327689876587 2”或“divpro 2 327689876587”的形式运行,将出现提示信息:“值超出了整数的表示范围”。
相关教程
关于我们--广告服务--免责声明--本站帮助-友情链接--版权声明--联系我们       黑ICP备07002182号