2011-06-28 33 views
1

我有兩個類,它們傳遞給序列化方法,我想在Serialization方法中訪問這些類的兩個屬性。問題是Serialization方法參數是作爲泛型傳遞的,我不知道如何在這種情況下訪問傳遞類的屬性。下面的例子。作爲泛型傳遞的訪問類屬性

public class MyClass1 
    { 

      public string MyProperty1 { get; set; } 

      //These properties are shared in both classes 
      public bool Result { get; set; } 
      public string EngineErrorMessage { get; set; } 

    } 
    public class MyClass2 
    { 

      public string MyProperty2 { get; set; } 

      //These properties are shared in both classes 
      public bool Result { get; set; } 
      public string EngineErrorMessage { get; set; } 

    } 


//The method is used to serialize classes above, classes are passed as generic types 
    public void Serialization<T>(ref T engine) 
      { 
       try 
       { 
       //Do some work with passed class 
       } 
       catch (Exception e) 
       { 

        //If Exception occurs I would like to write values to passed class properties, how to do that? 
        Result = false; 
        EngineErrorMessage = e.Message; 
       } 
    } 

全部方法的代碼

 public void Submit<T>(ref T engine) 
     { 
      try 
      { 

       var workingDir = Path.Combine(Settings.FileStoragePath, Helpers.GetRandomInt(9).ToString()); 



       Directory.CreateDirectory(workingDir); 
       var inputFile = Path.Combine(workingDir, Settings.InFileName); 
       var outputFile = Path.Combine(workingDir, Settings.OutFileName); 
       var deleteFile = Path.Combine(workingDir, Settings.DelFileName); 

       try 
       { 



        using (var stream = new FileStream(inputFile, FileMode.Create, FileAccess.Write, FileShare.None)) 
        { 
         Serializer.Serialize(stream, engine); 
        } 


        CheckStatus(outputFile); 


        using (var stream = new FileStream(outputFile, FileMode.Open, FileAccess.Read, FileShare.None)) 
        { 
         engine = Serializer.Deserialize<T>(stream);       
        } 


       } 
       finally 
       { 
        File.Create(deleteFile).Dispose(); 
       } 
      } 
      catch (Exception e) 
      { 
       //ToDo: Not implemented yet. 
/*    Result = false; 
       ErrorMessage = e.Message;*/ 
      } 
     } 
+0

順便說一句,這似乎不太可能,你需要用'參考一個序列化類的方法...是否有一個特定的原因呢? –

+0

我是C#的新手,使用你的序列化庫,我使用序列化和desiarialiaztion在一個方法。上面的代碼不是全部。所以爲了desializate並將值返回給類,我把它作爲參考。此外,如果我不會傳遞類作爲參考,我將無法分配這些類的Result和EngineErrorMessage屬性。對? – Tomas

+0

@Tomas即使沒有'ref',你仍然在傳遞實例的引用(因爲它是一個類),所以'.Result'和'EngineErrorMessage'仍然可以正常工作;真正的問題是您是否需要*爲參數分配一個新的對象*並讓調用者注意到重新分配*。然而,在大多數情況下,返回這樣一個值比較好,例如'void Serialize(T)'和'T Deserialize()'。 –

回答

3

聲明包含的屬性的接口ResultEngineErrorMessage。現在你有兩個選擇:

  1. 添加約束您的序列類型的參數,以便只從上述接口派生類型可序列化,或
  2. 在你的catch塊嘗試投engine到接口上文提到的。如果演員成功,請寫出屬性值,否則什麼都不做。

樣品:

public interface ISerializationErrorWriter 
{ 
    bool Result { set; get; } 
    string EngineErrorMessage { set; get; } 
} 

public class MyClass1 : ISerializationErrorWriter 
{ 
    public string MyProperty1 { get; set; } 

    public bool Result { get; set; } 
    public string EngineErrorMessage { get; set; } 
} 

public class MyClass2 : ISerializationErrorWriter 
{ 
    public string MyProperty2 { get; set; } 

    public bool Result { get; set; } 
    public string EngineErrorMessage { get; set; } 
} 

// Option 1: 
public void Serialization_1<T>(ref T engine) where T : ISerializationErrorWriter 
{ 
    try 
    { 
     //Do some work with passed class 
    } 
    catch (Exception e) 
    { 
     engine.Result = false; 
     engine.EngineErrorMessage = e.Message; 
    } 
} 

// Option 2: 
public void Serialization_2<T>(ref T engine) 
{ 
    try 
    { 
     //Do some work with passed class 
    } 
    catch (Exception e) 
    { 
     var serializationErrorWriter = engine as ISerializationErrorWriter; 
     if(serializationErrorWriter != null) 
     { 
      serializationErrorWriter.Result = false; 
      serializationErrorWriter.EngineErrorMessage = e.Message; 
     } 
    } 
} 
+0

這裏沒有太大的區別,但其中一個屬性是'MyProperty1',而不是2 –

+0

你說得很對。我通常不會複製和粘貼代碼:) –

+0

如果您在'ISerializationErrorWriter'中使用了屬性,那麼它會更重要,但您沒有 - 因此一切都很好。 –

2

你將不得不在某個時候使用反射,通過typeof(T)(或者engine.GetType())。如果這是一個頻繁的代碼路徑,您可能需要緩存每種類型的策略以避免開銷。或者可能更好:使用預先構建的序列化API來優化這種類型的場景(即其中大部分)。

如果你指的是ResultEngineErrorMessage,然後2種選擇:

  1. 就把這兩個屬性的界面上,實現從T 2種類型的接口,並添加where T : ISomeInterface約束Serialization<T>
  2. 使用dynamic鴨型到屬性
-1

如果只有兩個類來處理我覺得下面的序列化代碼的服務器,你也

//The method is used to serialize classes above, classes are passed as generic types 
       public void Serialization<T>(ref T engine) 
       { 
        try 
        { 
         Type genericType = typeof(T); 

         if (typeof(MyClass1).Equals(genericType)) 
         { 
          MyClass1 engineClass1 = engine as MyClass1; 
          //DO something for class 1 
         } 
         else if (typeof(MyClass2).Equals(genericType)) 
         { 
          MyClass2 engineClass2 = engine as MyClass2; 
          //DO something for class 2 
         } 

        } 
        catch (Exception e) 
        { 
         //If Exception occurs I would like to write values to passed class properties, how to do that? 
         Result = false; 
         EngineErrorMessage = e.Message; 
        } 
       } 
+0

對不起,但這並沒有回答這個問題。 OP想知道如何在'catch'塊中寫入'Result'和'EngineErrorMessage'屬性。 –

+0

ohk ..抱歉..我誤解了這個問題。 – Sumit