2012-12-16 204 views
17

我有一個對象,我想只在創建後纔讀取......也就是說,因爲構造函數中的屬性必須在GetHashCode中使用,因此無法更改一旦創建。創建泛型類型的實例時不能提供參數

我這是許多類是隻讀的一個:

public class AccountLabel 
{ 
    private string result; 

    public AccountLabel(string result) 
    { 
     // TODO: Complete member initialization 
     this.result = result; 
    } 

    public string JSONRPCData { get { return this.result; } } 
} 

我有這樣

public class JsonResult<T> where T : JObject, new() 
    { 
    private T bhash; 
    private string p; 
    private JsonErrorResponse error; 
    private int _id; 
    private Newtonsoft.Json.Linq.JObject ret; 

    public JsonResult(Newtonsoft.Json.Linq.JObject ret) 
    { 
     this.ret = ret; 

     var tempError = ret["error"]; 
     var tempid = ret["id"]; 
     JsonErrorResponse error = new JsonErrorResponse(tempError); 
     this.error = error; 
     this._id = 1; 


     var tempresult = ret["result"]; 
     T someResult = new T(tempresult); // <--- here is my problem 
    } 

我的問題的一般結果類是我想傳遞一個對象入T的構造函數但不能。當我輸入這個編譯器告訴我Cannot provide arguments when creating an instance of variable type

解決這種情況的最佳方法是什麼?

  • 我應該有一個我可以調用的接口來更新屬性嗎?

  • 以前的接口會破壞封裝還是允許對我的對象進行更改?

  • 我該怎麼辦?

+2

你可以創建一個Factory類,它知道如何創建T(所以JsonResult會調用MyFactory .create(tempresult)而不是使用新的 –

+0

我已經編輯過你的標題,請參閱「[應該包括」標籤「他們的標題?](http://meta.stackexchange.com/questions/19190/)「,其中共識是」不,他們不應該「。 –

回答

23

可以刪除new類型約束,並使用Activator.CreateInstance代替。

而是這個

T someResult = new T(tempresult); 

寫的:

T someResult = (T)Activator.CreateInstance(
    typeof(T) 
, new object[] { tempresult } 
); 

這很可能是有點慢,因爲通過反射去的,並且由編譯器靜態檢查將不會被執行。但是,考慮到您的情況,它看起來不像這些會在您的方案中出現重大問題。

7

你可以在工廠委託傳遞給的JSonResult<T>構造:在

public class JsonResult<T> where T : JObject 
{ 
    public JsonResult(Newtonsoft.Json.Linq.JObject ret, Func<object, T> factory) 
    { 
     var tempresult = ret["result"]; 
     T someResult = factory(tempresult); 
    } 
} 

object可以與任何的tempResult的類型實際上是被替換。

相關問題