2010-06-03 17 views
5

這是一個典型的函數,返回true/false;C#可能有一個通用的返回類型?

private static bool hasValue() 
{ 
    return true; 
} 

現在上的錯誤,我想和定義回到我自己的自定義錯誤對象:

public class Failure 
    { 
     public string FailureDateTime { get; set; } 
     public string FailureReason { get; set; } 
    } 

我本來期望能夠拋出這個自定義對象例如...

private static bool hasValue() 
{ 
    try 
     { 
      ...do something 
     } 
    catch 
     { 
     throw new Failure(); 
     } 
    return true; 
} 

這是不可能的,我不想從System.IO.Exception派生失敗,因爲我個人有問題序列化C#中的異常(這是與.net v2)。

這個問題的最佳實踐或理想解決方案是什麼?我應該只使用私有靜態對象嗎?還是有一種更清晰的方式來返回自定義對象或繞過錯誤(不使用System.IO.Exception)的典型返回類型?

我對於使用一個對象也不是完全瘋狂,因爲那麼我需要通過使用cast和更多布爾值來驗證結果。

+0

我覺得唯一可以拋出的東西是從異常派生的東西。 – kenny 2010-06-03 11:31:34

回答

10

這種解決方案可以適應這種情況:

var exception = new Exception(); 
exception.Data.Add("Failure", new Failure()); 
throw exception; 

您可以拋出異常(建議定義自己的異常類型),並使用數據字典持有的失敗。在catch代碼中,您可以獲取數據並將其序列化。如果您確實創建了自己的異常類型,則可以將故障置於屬性中。

評論:我沒有檢查它,但你確定例外是不可序列化的嗎?

+1

+1這很可愛。 – 2010-06-03 11:30:03

+0

我想我會實施這個解決方案,看起來很有希望。 – 2010-06-03 11:30:29

+0

我在實踐中遇到了一些序列化異常的問題。 – 2010-06-03 11:34:38

7

我不想從System.IO.Exception派生失敗,因爲無法序列化C#中的異常。

該問題基於的假設是,您不能序列化從IOException派生的異常。但是我想挑戰這個假設。 IOException被標記爲Serializable。你所要做的就是將你的子類標記爲可序列化的。

查看文檔IOException

[SerializableAttribute] 
[ComVisibleAttribute(true)] 
public class IOException : SystemException 
6

你需要從System.Exception(或任何其他非sealed子類)來推導,如果你想創建自己的異常類。如果你沒有序列化你正在談論的可能是你沒有實現序列化構造函數的事實。

Visual Studio有一個代碼片段,爲子類異常創建推薦的模板。您可以輸入exception並按標籤兩次獲得。

這是什麼出來:

[Serializable] 
public class MyException : Exception { 
    public MyException() { } 
    public MyException(string message) : base(message) { } 
    public MyException(string message, Exception inner) : base(message, inner) { } 
    protected MyException(
     System.Runtime.Serialization.SerializationInfo info, 
     System.Runtime.Serialization.StreamingContext context) 
     : base(info, context) { } 
} 
0

不要太擔心這種情況;只需創建一個結果類型來封裝所有這些邏輯。

public class ValueResult 
{ 
    public Failure FailureDetails {get;set;} 
    public bool Success {get;set;} 
    public bool HasValue {get;set;} 
    public object Value {get;set;} 
} 

從異常
var result = HasValue(); 
if(result.Success) 
    DoSomething(result.Value); 
else if(!result.Success) 
    LogFailure(result.FailureDetails); 
+1

...你可以用C風格的錯誤代碼獲得編程的優雅和健壯性......你如何讓調用者的調用者知道並處理錯誤? – 2010-06-03 11:47:38

+0

至少使它通用,而不是使用普通對象。 – harms 2010-06-03 11:53:54

+0

@harms價值是他想要的;該解決方案並不是要在任何情況下使用的通用類(無需替換異常處理),而只是他的問題的另一種選擇。所以如果Value應該是MintyGreenChocolate,他可以簡單地將它切換爲對象。 – Will 2010-06-03 16:18:27

0

你必須從異常繼承這樣的類:

[Serializable] 
public class Failure: Exception 
{ 
    public string ErrorMessage 
    { 
     get 
     { 
     return base.Message.ToString(); 
     } 
    } 

} 

然後

catch(Exception ex) 
{ 
    throw new Failure(
      "exception message here", ex.messege); 
} 
0

您也可以隨時使用企業庫的異常處理自定義異常提供自己的異常處理類,格式類型,測井等..

try 
{ 
} 
catch(Exception ex) 
{ 
    bool rethrow = ExceptionPolicy.HandleException(ex, "My Custom Policy"); 
    if (rethrow) 
    { 
     throw; 
    } 
} 
finally 
{ 
} 

例子:

http://weblogs.asp.net/sukumarraju/archive/2009/10/04/microsoft-enterprise-library-4-1-exception-handling-block.aspx

http://www.imason.com/imason_Blogs/b/suleman_ibrahim/archive/2009/05/25/configuring-enterprise-library-4-0-for-exception-handling-and-logging.aspx