寫完這一篇,大概可以準備過年了,就算是這系列文章的收尾吧。
異常處理語句,就是常說的try...catch語句,有時候,也會帶有finally子句。要生成異常處理語句,得用到CodeTryCatchFinallyStatement類,它包含三個部分。
1、TryStatements:嘗試執行的代碼塊。
2、CatchClauses:捕捉異常的代碼塊。CatchClauses是一個子句集合,因為一個try語句可以包含N個catch子句,而每個catch塊都由CodeCatchClause類來表示,使用時應提供要捕捉的異常的類型,異常對象的臨時變量名,以及catch塊的語句集合。
3、FinallyStatements:finally語句塊,不管會不會發生異常,finally中的語句會執行。
下面看一個最常見的try語句的生成。
CodeTryCatchFinallyStatement trycatfanStatement = new CodeTryCatchFinallyStatement();
trycatfanStatement.TryStatements.Add(new CodeCommentStatement("試着執行"));
CodeCatchClause catClause = new CodeCatchClause();
// 異常類型
catClause.CatchExceptionType = new CodeTypeReference(typeof(Exception));
// 臨時變量名
catClause.LocalName = "ex";
// catch塊中的語句
catClause.Statements.Add(new CodeMethodInvokeExpression(new CodeMethodReferenceExpression(new CodeTypeReferenceExpression(typeof(Console)), nameof(Console.WriteLine)), new CodePropertyReferenceExpression(new CodeVariableReferenceExpression("ex"), nameof(Exception.Message))));
// 記得将 CodeCatchClause 對象加入到 CatchClauses 集合中
trycatfanStatement.CatchClauses.Add(catClause);
CodeDomProvider provider = CodeDomProvider.CreateProvider("cs");
provider.GenerateCodeFromStatement(trycatfanStatement, Console.Out, null);
以上代碼隻生成了try和catch兩個子塊,這種形式是最為常見的。其生成的代碼如下。

當然,如果需要,還可以添加上 finally 塊,在上面的示例代碼中加入以下代碼:
trycatfanStatement.FinallyStatements.Add(new CodeCommentStatement("清理操作"));
然後生成的代碼中就會包含 finally 塊了。
try 語句可以包括多個 catch 子句,比如這樣。
CodeTryCatchFinallyStatement trystatement = new CodeTryCatchFinallyStatement();
trystatement.TryStatements.Add(new CodeCommentStatement("待執行代碼"));
// 第一個 catch 子句
CodeCatchClause catch1 = new CodeCatchClause();
catch1.CatchExceptionType = new CodeTypeReference(typeof(FormatException));
catch1.LocalName = "fex";
catch1.Statements.Add(new CodeCommentStatement("捕捉異常"));
trystatement.CatchClauses.Add(catch1);
// 第二個 catch 子句
CodeCatchClause catch2 = new CodeCatchClause();
catch2.CatchExceptionType = new CodeTypeReference(typeof(ArgumentException));
catch2.LocalName = "gex";
catch2.Statements.Add(new CodeCommentStatement("捕捉異常"));
trystatement.CatchClauses.Add(catch2);
CodeDomProvider p = CodeDomProvider.CreateProvider("C#");
p.GenerateCodeFromStatement(trystatement, Console.Out, null);
以上代碼生成的try語句包含兩個catch子句,分别捕捉FormatException和ArgumentException兩種類型的異常。生成的代碼如下。
順便也說說抛出異常的語句,使用的是 CodeThrowExceptionStatement 類,例如
CodeThrowExceptionStatement ts = new CodeThrowExceptionStatement(new CodeObjectCreateExpression(typeof(FieldAccessException)));
生成的throw語句如下圖所示。
傳遞給 CodeThrowExceptionStatement 構造函數的參數為要抛出的異常對象,本例直接用new關鍵字來建立異常執行個體。如果明确定義了異常變量,可以引用變量。就像這樣。
CodeVariableDeclarationStatement vd = new CodeVariableDeclarationStatement(typeof(EncoderFallbackException), "ex", new CodeObjectCreateExpression(typeof(EncoderFallbackException)));
CodeThrowExceptionStatement ts = new CodeThrowExceptionStatement(new CodeVariableReferenceExpression("ex"));
CodeDomProvider p = CodeDomProvider.CreateProvider("cs");
p.GenerateCodeFromStatement(vd, Console.Out, null);
p.GenerateCodeFromStatement(ts, Console.Out, null);
生成的代碼如下。
===========================================
好了,Code DOM 系列文章就寫完了。
過年後,如果能趕上 Windows 10 “紅石2”的更新,那咱們就繼續聊 UWP 相關的内容。
提前祝大夥新春快樂。