因為現在工作的環境關係,需要使用到Net1.1開發,所以很多功能都沒有,其中也包含了List
如果在某類別定義中,包含了ArrayList成員,由於ArrayList存放的是Object型別物件,所以在做反序列化時,會出現型態轉換的問題,以下來介紹與處理。
前言
因為現在工作的環境關係,需要使用到Net1.1開發,所以很多功能都沒有,其中也包含了List<T>此泛型串列,所以在Net1.1上都是使用ArrayList在做儲存,而此時便出現了一個問題
如果在某類別定義中,包含了ArrayList成員,由於ArrayList存放的是Object型別物件,所以在做反序列化時,會出現型態轉換的問題,以下來介紹與處理。
類別中包含ArrayList的例子
在使用Json序列化與反序列化上,由於是把NT上的資料透過WebService傳送到較新的主機上,所以新的主機上開發環境不存在Net1.1,也因此直接使用Json.Net去做反序列化。
而在反序列化前,我要反序列化成的類別定義類似如下:
這是一個紀錄新增移除中,每一項安裝軟體的基本資訊,其中softwareAppProgramDetail 是一個ArrayList ,裡面的每一項資料保存的是ExecutableProgramDetail型別物件,代表了這個安裝軟體相關的各個執行檔資訊。
public class InstalledSoftwareInfo
{
public InstalledSoftwareInfo()
{
softwareAppProgramDetail = new ArrayList();
}
private string displayName;
//..Other Code
private ArrayList softwareAppProgramDetail; //保存的是ExecutableProgramDetail型別的物件
}
然後因為會有很多InstalledSoftwareInfo型別物件,所以另外又用一個ArrayList保存,如下:
ArrayList installedSoftwares = new ArrayList ();
installedSoftwares .Add( installedSoftwares ); //installedSoftwares 是InstalledSoftwareInfo型別物件,裡頭包含了許多與installedSoftwares相關的執行檔案。
遇到的錯誤訊息
一開始我做反序列化時,因為在WebService上的主機可以使用新的.Net,所以使用List<T>的方式取回資料。沒有想太多,很直覺得做法是`:
//轉換格式
List<installedsoftwareinfo> installedSoftwares = JsonConvert.DeserializeObject>(jsonString);
拿到了各個新增移除中的軟體資訊後,再來是取得各個軟體資訊中相關的執行檔案,如下:
foreach (InstalledSoftwareInfo installedSoftware in installedSoftwares){
List<ExecutableProgramDetail> appDetails = installedSoftware.SoftwareAppProgramsDetail.Cast<ExecutableProgramDetail>().ToList();
//… Other Code
}
於是在執行時,出現了以下錯誤:
Newtonsoft.Json.JsonSerializationException: Cannot deserialize the current JSON array (e.g. [1,2,3]) into type 'AgentReceiverWebServiceFormSample.AgentReceiverWS+obJson' because the type requires a JSON object (e.g. {"name":"value"}) to deserialize correctly.
To fix this error either change the JSON to a JSON object (e.g. {"name":"value"}) or change the deserialized type to an array or a type that implements a collection interface (e.g. ICollection, IList) like List<T> that can be deserialized from a JSON array. JsonArrayAttribute can also be added to the type to force it to deserialize from a JSON array.
Path ''
原因與處理方法
其實想一下就是知原因的問題,因為一開始在做反序列化時,轉換成InstalledSoftwareInfo類別,因為裡面是ArrayList,所以無法把那部分的內部的Json字串做一個對應的轉換為ExecutableProgramDetail,而是以String型別的方式保存下來。
所以如果把資料印出來會是仍以Json格式的字串顯示installedSoftware.SoftwareAppProgramsDetail的每一筆資料,因此我們處理方式應是如下:
foreach (InstalledSoftwareInfo installedSoftware in installedSoftwares){
ArrayList array = installedSoftware.SoftwareAppProgramsDetail;
for (int j = 0; j < array.Count; j++)
{
string appDetailStr = array[j].ToString();
//對ArrayList反序列化(因為ArrayList無法解析所以裡頭是Json字串)
ExecutableProgramDetail appDetail = JsonConvert.DeserializeObject<ExecutableProgramDetail>(appDetailStr);
//Other code..
}
}
在做一次反序列化,把SoftwareAppProgramsDetail中的每一筆Json字串做反序列化,才可以拿到ArrayList中應該要的ExecutableProgramDetail 型別資料。
後記
真的很少在使用ArrayList,都是用List<T>,所以便沒有注意到有這些問題,所以也是一個備忘記錄,如果剛好有遇到此狀況,此篇希望能協助到您。
文章中的敘述如有觀念不正確錯誤的部分,歡迎告知指正 謝謝 =)
另外要轉載請附上出處 感謝