『難道不能直接改參數類別(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』且有『預設建構式』
沒有留言:
張貼留言