異常是程序執(zhí)行過(guò)程中產(chǎn)生的問(wèn)題。C# 異常是對(duì)程序運(yùn)行過(guò)程中出現(xiàn)的額外情況的一種反饋,例如除數(shù)為零時(shí)。
異常提供了一種將控制權(quán)從程序的一個(gè)部分轉(zhuǎn)移到另一個(gè)部分的方式。C# 異常處理有四個(gè)關(guān)鍵詞:try,catch,finally,throw。
假設(shè)一個(gè)代碼塊產(chǎn)生了一個(gè)異常,通過(guò)使用 try 和 catch 的組合可以捕獲這個(gè)異常。一個(gè) try/catch 代碼塊需要放置在可能會(huì)產(chǎn)生異常的代碼段周?chē)?。try/catch 代碼段就像是保護(hù)代碼,它的使用語(yǔ)法如下:
try
{
// statements causing exception
}
catch( ExceptionName e1 )
{
// error handling code
}
catch( ExceptionName e2 )
{
// error handling code
}
catch( ExceptionName eN )
{
// error handling code
}
finally
{
// statements to be executed
}
當(dāng)你的 try 語(yǔ)句塊可能會(huì)拋出多種異常時(shí),你可以列出多種的 catch 語(yǔ)句,以便捕獲不同種類(lèi)的異常。
C# 異常由類(lèi)表示。在 C# 中的異常類(lèi)主要是直接或間接地來(lái)源于 System.Exception 類(lèi)。有些從 System.Exception 類(lèi)派生的異常類(lèi),它們是 System.ApplicationException 和 System.SystemException 類(lèi)。
System.ApplicationException 類(lèi)支持由應(yīng)用程序生成的異常。因此,由程序員定義的異常應(yīng)該源于這個(gè)類(lèi)。
System.SystemException 類(lèi)是所有預(yù)定義的系統(tǒng)異常的基類(lèi)。
下表提供了一些從 Sytem.SystemException 類(lèi)派生的預(yù)定義的異常類(lèi):
| Exception類(lèi) | 描述 |
|---|---|
| System.IO.IOException | 處理 I/O 錯(cuò)誤 |
| System.IndexOutOfRangeException | 處理的方法是指當(dāng)一個(gè)數(shù)組索引超出范圍的錯(cuò)誤產(chǎn)生 |
| System.ArrayTypeMismatchException | 處理時(shí),類(lèi)型不匹配的數(shù)組類(lèi)型產(chǎn)生的錯(cuò)誤 |
| System.NullReferenceException | 處理從取消引用一個(gè)空對(duì)象產(chǎn)生的錯(cuò)誤 |
| System.DivideByZeroException | 處理來(lái)自將一個(gè)除零而產(chǎn)生的錯(cuò)誤 |
| System.InvalidCastException | 處理類(lèi)型轉(zhuǎn)換過(guò)程中產(chǎn)生的錯(cuò)誤 |
| System.OutOfMemoryException | 處理來(lái)自可用內(nèi)存不足產(chǎn)生的錯(cuò)誤 |
| System.StackOverflowException | 處理從堆棧溢出產(chǎn)生的錯(cuò)誤 |
C# 為在 try catch 語(yǔ)句塊中處理異常提供了一種結(jié)構(gòu)化的解決方案。這種方法可以使核心代碼段和異常處理部分分離開(kāi)。
這些異常處理代碼段是通過(guò)使用 try,catch,finally 關(guān)鍵字實(shí)現(xiàn)的。下面是一個(gè)除數(shù)為零的異常處理情況:
using System;
namespace ErrorHandlingApplication
{
class DivNumbers
{
int result;
DivNumbers()
{
result = 0;
}
public void division(int num1, int num2)
{
try
{
result = num1 / num2;
}
catch (DivideByZeroException e)
{
Console.WriteLine("Exception caught: {0}", e);
}
finally
{
.WriteLine("Result: {0}", result);
}
}
static void Main(string[] args)
{
DivNumbers d = new DivNumbers();
d.division(25, 0);
Console.ReadKey();
}
}
}
編譯執(zhí)行上述代碼,得到如下結(jié)果:
Exception caught: System.DivideByZeroException: Attempted to divide by zero.
at ...
Result: 0
你也可以定義你自己的異常。自定義異常類(lèi)繼承自 ApplicationException 類(lèi)。示范如下:
using System;
namespace UserDefinedException
{
class TestTemperature
{
static void Main(string[] args)
{
Temperature temp = new Temperature();
try
{
temp.showTemp();
}
catch(TempIsZeroException e)
{
Console.WriteLine("TempIsZeroException: {0}", e.Message);
}
Console.ReadKey();
}
}
}
public class TempIsZeroException: ApplicationException
{
public TempIsZeroException(string message): base(message)
{
}
}
public class Temperature
{
int temperature = 0;
public void showTemp()
{
if(temperature == 0)
{
throw (new TempIsZeroException("Zero Temperature found"));
}
else
{
Console.WriteLine("Temperature: {0}", temperature);
}
}
}
編譯執(zhí)行上述代碼,得到如下結(jié)果:
TempIsZeroException: Zero Temperature found
如果某個(gè)對(duì)象是直接或間接地繼承自 System.Exception 類(lèi),你可以拋出這個(gè)對(duì)象。你可以在 catch 語(yǔ)句塊中用 throw 語(yǔ)句拋出這個(gè)對(duì)象:
Catch(Exception e)
{
...
Throw e
}