『難道不能直接改參數類別(Class),就對應到參數檔(xml)嗎?不想逐步修改loadIniFile()、saveIniFile()內容』是的,我們可以靠序列化(Serialization)達成,參考MSDN文章得知:
序列化是將物件(Object)轉換為位元組資料流(Stream of bytes)的一種處理程序,以便將其儲存或傳輸至記憶體、資料庫或檔案。主要目的是要儲存物件的狀態,以便能在需要時重新建立該物件。此回復程序稱為還原序列化 (Deserialization)。
上述的”物件”我們直接當成參數類別的實體(Instance),是以整個物件做序列化,不需要針對物件中的個別參數寫檔案,或是讀檔案後一一寫到參數。對應我們的目標,流程可以簡述如下:
- 序列化 : 物件 -> 位元資料流 -> 存檔
- 反序列化 : 讀檔 -> 位元資料流 -> 物件
- 存檔文件的可讀性: 序列化方式不只有一種,可以選用XML序列化,讓文檔具有可讀性。
- 程式寫法解耦: 單說解耦有點抽象,但其實就是要把功能寫成通用、獨立的函式,目標是用一個函式把物件序列化為文件,和一個函式反序列化文件為物件。
- 類別和屬性的標籤簡化: 要序列化的類別和屬性通常都要標示[Serializable()]之類的特性,但都已經建立專屬的參數類別了,本來就要把整個類別序列化,標示特性的動作還是有點瑣碎。
//將物件序列化為檔案 public static void WriteToXml<T>(string fullFileName , T instance) { FileStream writer = null; string directory = Path.GetDirectoryName(fullFileName); if (!Directory.Exists(directory)) { Directory.CreateDirectory(directory); } try { writer = new FileStream(fullFileName , FileMode.Create); DataContractSerializer ser = new DataContractSerializer(instance.GetType()); ser.WriteObject(writer , instance); writer.Close(); } catch (Exception ex) { if (writer != null) { writer.Close(); } throw new Exception(ex.Message); } }
//反序列化檔案為物件 public static T ReadFromXml<T>(string fullFileName) { FileStream fs = null; try { fs = new FileStream(fullFileName , FileMode.Open); DataContractSerializer ser = new DataContractSerializer(typeof(T)); T deserializedData = (T)ser.ReadObject(fs); fs.Close(); return deserializedData; } catch (Exception ex) { if (fs != null) { fs.Close(); } throw new Exception(ex.Message); } }
範例下載
2016/07/04 補充: 參數類別一定要是『public』且有『預設建構式』