如何反序列化xml字符串
我试图反序列化一个xml字符串,我没有反序列化对象。
我的xml字符串看起来像
123445 78945
[Serializable()] [XmlRoot("Cars")] public class Cars { [XmlArrayItem("Car",typeof(Car))] public Car[] Car { get; set; } } [Serializable()] public class Car { [XmlElement("Id")] public long Id { get; set; } [XmlArrayItem("BMW",typeof(BMW))] public BMW[] BMW { get; set; } } [Serializable()] public class BMW { [XmlElement("Id")] public long Id { get; set; } }
这是我正在尝试的代码:
string str = "xml string like above"; XmlSerializer ser = new XmlSerializer(typeof(Cars)); var wrapper = (Cars) ser.Deserialize(new StringReader(str));
而且我确实有像BMW里面的几个子arrays对象。 BUt它不是序列化汽车。 有人可以在这里指出我的错误吗?
尝试使用XmlElement
而不是XmlArrayItem
因为这些项没有封装标记:
[Serializable()] [XmlRoot("Cars")] public class Cars { [XmlElement("Car",typeof(Car))] public Car[] Car { get; set; } } [Serializable()] public class Car { [XmlElement("Id")] public long Id { get; set; } [XmlElement("BMW",typeof(BMW))] public BMW[] BMW { get; set; } }
尝试将预期对象序列化为xml并进行比较。 (Serialize方法比Deserialize更容易。)这可能会突出显示错误放置或错误命名的属性。
我有几个建议和一个很好的工作示例。 首先,我建议使用不同的类结构来利用类层次结构。
这是你需要的:
- CarList – 用于管理汽车列表的包装类
- Car – 提供所有基本Car属性和方法的类
- 宝马 – 特定类型的汽车级。 它inheritance了父Car类并提供了其他属性和方法。
当您想要添加更多Car类型时,您将创建另一个类并让它inheritanceCar类。
关于代码……
这是你的CarList课程。 请注意,Car对象列表上有多个XmlElement声明。 这样序列化/反序列化就知道如何处理不同的Car类型。 当您添加更多类型时,您必须在此处添加一行来描述类型。
另外,请注意处理序列化/反序列化的静态Save和Load方法。
[XmlRoot("CarList")] public class CarList { [XmlAttribute("Name")] public string Name { get; set; } [XmlElement("Cars")] [XmlElement("BWM", typeof(BMW))] [XmlElement("Acura", typeof(Acura))] //[XmlArrayItem("Honda", typeof(Honda))] public List Cars { get; set; } public static CarList Load(string xmlFile) { CarList carList = new CarList(); XmlSerializer s = new XmlSerializer(typeof(CarList)); TextReader r = new StreamReader(xmlFile); carList = (CarList)s.Deserialize(r); r.Close(); return carList; } public static void Save(CarList carList, string fullFilePath) { XmlSerializer s = new XmlSerializer(typeof(CarList)); TextWriter w = new StreamWriter(fullFilePath); // use empty namespace to remove namespace declaration XmlSerializerNamespaces ns = new XmlSerializerNamespaces(); ns.Add("", ""); s.Serialize(w, carList, ns); w.Close(); } }
接下来,这是你的汽车课……
public class Car { // put properties and methods common to all car types here [XmlAttribute("Id")] public long Id { get; set; } }
最后,您的特定车型……
public class BMW : Car { // put properties and methods specific to this type here [XmlAttribute("NavVendor")] public string navigationSystemVendor { get; set; } } public class Acura : Car { // put properties and methods specific to this type here [XmlAttribute("SunroofTint")] public bool sunroofTint { get; set; } }
像这样加载你的CarList:
CarList carList = CarList.Load(@"C:\cars.xml");
进行一些更改,然后保存您的CarList,如下所示:
CarList.Save(carList, @"C:\cars.xml");
以下是XML的样子:
希望这有助于您开始朝着正确的方向前进!
我想我发现了问题。 我没有包括我在xml中获取的所有属性。 如果您错过任何属性,反序列化将无效。 我还添加了这样的行:
[XmlArray(Form = XmlSchemaForm.Unqualified), XmlArrayItem("BMW", typeof(BMW), Form = XmlSchemaForm.Unqualified, IsNullable = false)] public BMW[] BMWs { get; set; }
如果你的xml有这样的东西:
123445 78945
然后它奏效了。 我没有任何XSD或架构来生成我认为理想的opbject。