现在的位置: 首页 > 综合 > 正文

定义自定义的异常

2013年09月22日 ⁄ 综合 ⁄ 共 10949字 ⁄ 字号 评论关闭
首先我们建立自己的异常类CustomException,它要继承自ApplicationException类(这是一个在发生非致命的应用程序错误时抛出的通用异常,它又继承于更为通用的Exception类),将其用作为应用程序定义的任何自定义异常的基类。通过这个基类,我们就可以编写一个通用的catch代码块,捕获应用程序定义的任何自定义异常类型。
自定义的异常类型可以在这中间扮演一个非常重要的角色。我们可以捕获一个通用的异常,识别它和应用程序的关系,然后把它作为特定于应用程序的异常再次抛出,以便能适当地处理它。
这里构建了一个简单的场景,使用Northwind数据库,向其中添加一条Customer记录,如果ID重复则抛出相应的异常信息。
 (1) 定义我们的基础异常类
    public class CustomException:ApplicationException
    {
        public CustomException()
        {
        }
         public CustomException(string message, Exception inner):base(message,inner)
        {
        }
    }
定义两个处理异常的方法,使用base关键字让CustomException方法继承自基本的错误异常类ApplicationException并提供了两个参数,一个异常消息参数和一个异常错误类。
(2) 然后我们再定一个处理我们不同自定义错误类型的错误处理类,不同的应用程序异常类型使用不同的异常处理类。
    public class DuplicateCustomerIDException : CustomException
    {
        public DuplicateCustomerIDException()
        {
        }
         public DuplicateCustomerIDException(string message, Exception inner):base(message,inner)
        {
        }
    }
当出现相应类型的异常时,在这个自定义异常处理中可以在出现错误的时候做一系列的处理,然后再抛出异常信息,例如:记录错误日志,或者做容错处理等。
(3) 最后我们在添加客户记录的时候,使用我们自定义的异常
        private void AddCustomerRecord()
        {
            SqlConnection cn = new SqlConnection(DBConn);
            cn.Open();
             try
            {
                SqlCommand com = new SqlCommand("Insert Into Customers (CustomerID,CompanyName,ContactName) Values ('"+ftxt_CustomerID.Text+"','"+ftxt_CompanyName.Text+"','"+ftxt_ContactName.Text+"')",cn);
                com.ExecuteNonQuery();
            }
            catch(SqlException ex)
            {
                if(ex.Number == 2627)
                {
                    throw new DuplicateCustomerIDException("CustomerID重复",ex);
                }
                else
                {
                    MessageBox.Show("成功","提示信息",MessageBoxButtons.OK,MessageBoxIcon.Information,MessageBoxDefaultButton.Button1,MessageBoxOptions.DefaultDesktopOnly);
                }
            }
            finally
            {
                cn.Close();
            }
        }
其中的ex.Number == 2627就是由于数据表中主键重复不能添加重复主键的记录时抛出的异常号码,如果异常类型符合怎抛出我们自定义的异常处理类。
(4) 最后我们在调用这个方法时,编写代码捕获这个我们自定义类型的异常
        private void fbtn_Submit_Click(object sender, System.EventArgs e)
        {
            try
            {
                AddCustomerRecord();
            }
            catch(DuplicateCustomerIDException ex)
            {
                MessageBox.Show(ex.Message);
            }
        }
 For Example :
private void AddCustomerRecord()
{
SqlConnection cn = new SqlConnection(DBConn);
cn.Open();

try
{
SqlCommand com = new SqlCommand("Insert Into Customers (CustomerID,CompanyName,ContactName) Values ('"+ftxt_CustomerID.Text+"','"+ftxt_CompanyName.Text+"','"+ftxt_ContactName.Text+"')",cn);

com.ExecuteNonQuery();
}

catch(SqlException ex)
{
if(ex.Number == 2627)
{
throw new Exception ("CustomerID重复");
}
else
{
MessageBox.Show("成功","提示信息",MessageBoxButtons.OK,MessageBoxIcon.Information,MessageBoxDefaultButton.Button1,MessageBoxOptions.DefaultDesktopOnly);

}
}
finally
{
cn.Close();
}
}

捕获
try

{

AddCustomerRecord();

}

catch(Exception ex)

{

MessageBox.Show(ex.InnerException.Message);

}

以XML为错误信息资源的自定义异常处理
 1、先做个xml,用来存储异常信息。文件名:MsgsResource.xml  
  <?xml   version="1.0"   encoding="utf-8"   ?>    
  <messages>  
          <message   id="0">  
                  <title>数据提供问题</title>  
                  <body>没有找到数据的提供地方</body>  
          </message>  
          <message   id="1">  
                  <title>地址错误</title>  
                  <body>页面地址错误或者地址参数错误</body>  
          </message>  
  </messages>  
  2、再做一个用来存msgs的用来存title和body的构造体,类名为CustomExceptionType.cs  
          public   class   ExceptionMsg  
          {  
                  private   int   messageid=-1;  
                  private   string   title="";  
                  private   string   body="";  
   
                  public   int   MessageId  
                  {  
                          get   {   return   messageid;   }  
                          set   {   messageid=value;   }  
                  }  
   
                  public   string   Title    
                  {  
                          get   {   return   title;   }  
                          set   {   title=value;   }  
                  }  
   
                  public   string   Body    
                  {  
                          get   {   return   body;   }  
                          set   {   body=value;   }  
                  }  
          }然后再做个读xml的类,这个类要传个id的参数进去作为查找。类名:ExceptionMsgsManager.cs  
                  public   ExceptionMsgsManager()  
                  {  
                          //如果Cache为空的话才执行  
                          if   (HttpRuntime.Cache["ExceptionMsgs"]   ==   null)    
                          {                                  
                                  Hashtable   MsgsTable=new   Hashtable();//定义一个哈希表用来存储错误信息的集合  
                                  ExceptionMsg   em;  
   
                                  XmlDocument   doc=new   XmlDocument();  
                                  string   XmlPath=HttpContext.Current.Server.MapPath("MsgsResource.xml");  
                                  doc.Load(XmlPath);  
                                  XmlNode   UrlsRoot=doc.SelectSingleNode("messages");  
                                  foreach   (XmlNode   node   in   UrlsRoot.ChildNodes)  
                                  {  
                                          em=new   ExceptionMsg();  
   
                                          //用数据构造体装载xml的内容  
                                          em.MessageId=int.Parse(node.Attributes["id"].Value);  
                                          em.Title=node.SelectSingleNode("title").InnerText;  
                                          em.Body=node.SelectSingleNode("body").InnerText;  
   
                                          //将填充好的em加载到哈希表里  
                                          MsgsTable[em.MessageId]=em;  
                                  }  
                                  //将完整的哈希表插入到Cache  
                                  HttpRuntime.Cache.Insert("ExceptionMsgs",   MsgsTable   ,   null,   DateTime.MaxValue,   TimeSpan.Zero);  
                          }  
                  }  
   
                  /**////   <summary>  
                  ///   读取异常信息的Hashtable  
                  ///   </summary>  
                  ///   <param   name="MessageId">这个是xml中的messageid</param>  
                  ///   <returns></returns>  
                  public   ExceptionMsg   GetExceptionMsg(int   MessageId)  
                  {  
                          Hashtable   Msgs=(Hashtable)HttpRuntime.Cache["ExceptionMsgs"];  
                          return   (ExceptionMsg)Msgs[MessageId];  
                  }  
  3、做一个友好的界面,也就是做一个输出错误信息的页,pageload的事件里就request出地址参数,文件名:WebForm1.aspx  
                  private   void   Page_Load(object   sender,   System.EventArgs   e)  
                  {  
                          int   msgid=int.Parse(Request["msgid"]);  
                          //GetExceptionMsg我将他做成了静态方法,大家可以自己做一个静态方法,且这个页很简单,我就不详细写了  
                          Response.Write(GetExceptionMsg(msgid).Title);  
                          Response.Write("<br>");  
                          Response.Write(GetExceptionMsg(msgid).Body);  
                  }  
  4、关键的东西开始了~要认真看哦,首先自定义一个异常的枚举类型,类型名:CustomExceptionType.cs  
          public   enum   CustomExceptionType  
          {  
                  DataProvider   =   0,//数据提供错误  
                  PageUrlError   =   1//地址错误  
          }  
   
  5、然后要写一个自定义的异常处理类,在这个类的重写方法全用自定义的异常类型,这个类继承了ApplicationException,再多态了一下。(这个我想是写注析的,但后来不知道怎样写好,只会让大家意会了)
类名:CustomException.cs  
          public   class   CustomException   :   ApplicationException  
          {  
                  成员#region   成员  
   
                  CustomExceptionType   exceptionType;  
   
                  public   CustomExceptionType   ExceptionType    
                  {  
                          get    
                          {  
                                  return   exceptionType;  
                          }  
                  }  
   
                  #endregion  
   
                  构造函数#region   构造函数  
   
                  public   CustomException(CustomExceptionType   t)   :   base()    
                  {  
                          Init();  
                          this.exceptionType   =   t;    
                  }  
   
                  public   CustomException(CustomExceptionType   t,   string   message)   :   base(message)    
                  {  
                          Init();  
                          this.exceptionType   =   t;  
                  }  
   
                  public   CustomException(CustomExceptionType   t,   string   message,   Exception   inner)   :   base(message,   inner)    
                  {  
                          Init();  
                          this.exceptionType   =   t;    
                  }  
   
                  #endregion  
   
                  重写的方法#region   重写的方法  
   
                  public   override   string   Message    
                  {  
                          get  
                          {  
  //                                 具体处理可以放在这里  
  //                                 switch   (exceptionType)    
  //                                 {                                                  
  //                                         case   CustomExceptionType.UserNotFound:  
  //                                                 return   string.Format(ResourceManager.GetString("Exception_UserNotFound"),   base.Message);  
  //                                 }  
                                  return   base.Message;  
                          }  
                  }  
   
                  public   override   int   GetHashCode()    
                  {  
                          string   stringToHash   =   (   exceptionType   +   base.Message);  
   
                          return   stringToHash.GetHashCode();  
                           
                  }  
   
                  #endregion  
   
                  错误产生的属性#region   错误产生的属性                  
                  string   userAgent   =   string.Empty;  
                  public   string   UserAgent    
                  {  
                          get   {   return   userAgent;   }  
                          set   {   userAgent   =   value;   }  
                  }  
   
                  public   int   Category    
                  {  
                          get   {   return   (int)   exceptionType;   }  
                          set   {   exceptionType   =   (CustomExceptionType)   value;   }  
                  }  
   
                  string   ipAddress   =   string.Empty;  
                  public   string   IPAddress    
                  {  
                          get   {   return   ipAddress;   }  
                          set   {   ipAddress   =   value;   }  
                  }  
   
                  string   httpReferrer   =   string.Empty;  
                  public   string   HttpReferrer    
                  {  
                          get   {   return   httpReferrer;   }  
                          set   {   httpReferrer   =   value;   }  
                  }  
   
                  string   httpVerb   =   string.Empty;  
                  public   string   HttpVerb    
                  {  
                          get   {   return   httpVerb;   }  
                          set   {   httpVerb   =   value;   }  
                  }  
   
                  string   httpPathAndQuery   =   string.Empty;  
                  public   string   HttpPathAndQuery    
                  {  
                          get   {   return   httpPathAndQuery;   }  
                          set   {   httpPathAndQuery   =   value;   }  
                  }  
   
                  DateTime   dateCreated;  
                  public   DateTime   DateCreated    
                  {  
                          get   {   return   dateCreated;   }  
                          set   {   dateCreated   =   value;   }  
                  }  
   
                  DateTime   dateLastOccurred;  
                  public   DateTime   DateLastOccurred    
                  {  
                          get   {   return   dateLastOccurred;   }  
                          set   {   dateLastOccurred   =   value;   }  
                  }  
                  int   frequency   =   0;  
                  public   int   Frequency    
                  {  
                          get   {   return   frequency;   }  
                          set   {   frequency   =   value;   }  
                  }  
   
                  string   stackTrace   =   string.Empty;  
                  public   string   LoggedStackTrace    
                  {  
                          get    
                          {  
                                  return   stackTrace;  
                          }  
                          set    
                          {  
                                  stackTrace   =   value;  
                          }  
                  }  
   
                  int   exceptionID   =   0;  
                  public   int   ExceptionID    
                  {  
                          get    
                          {  
                                  return   exceptionID;  
                          }  
                          set    
                          {  
                                  exceptionID   =   value;  
                          }  
                  }  
                  #endregion  
   
                  异常产生后要做的事情#region   异常产生后要做的事情  
   
                  private   void   Init()  
                  {  
                          //这里暂时为空,要用到的时候再写  
                  }  
   
                  #endregion  
          }  
   
  6、在Global.asax的Application_Error中做抛出错误后的处理  
                          //先判断是否为自己定义的异常  
                          if(Server.GetLastError().GetBaseException()   is   CustomException)  
                          {  
                                  //把抛出的异常的信息读出来  
                                  CustomException   ce=(CustomException)Server.GetLastError().GetBaseException();  
                                  //带上异常信息的ID跳到错误页  
                                  Response.Redirect("webform1.aspx?msgid="+ce.ExceptionID,true);  
                          }  
  7、最后的一步....测试  
                          try  
                          {  
                                                  //随便写点东西  
                                                          SqlConnection   conn=........;  
                                                          conn.Open();  
                                  }  
                          catch  
                          {   //没什么好说的,就是势出刚才的劳动成果  
                                  throw   new   CustomException(CustomExceptionType.DataProvider)   ;  
                          }  

 

抱歉!评论已关闭.