Deserialization Issues Object List

I am having trouble deserializing a list of objects. I can only get one object to serialize into an object, but I can not get the list. I am not getting errors, it just returns an empty list. This is returned by XML:

<locations> <location locationtype="building" locationtypeid="1"> <id>1</id> <name>Building Name</name> <description>Description of Building</description> </location> </locations> 

This is the class I have and deserialize in the GetAll method:

 [Serializable()] [XmlRoot("location")] public class Building { private string method; [XmlElement("id")] public int LocationID { get; set; } [XmlElement("name")] public string Name { get; set; } [XmlElement("description")] public string Description { get; set; } [XmlElement("mubuildingid")] public string MUBuildingID { get; set; } public List<Building> GetAll() { var listBuildings = new List<Building>(); var building = new Building(); var request = WebRequest.Create(method) as HttpWebRequest; var response = request.GetResponse() as HttpWebResponse; var streamReader = new StreamReader(response.GetResponseStream()); TextReader reader = streamReader; var serializer = new XmlSerializer(typeof(List<Building>), new XmlRootAttribute() { ElementName = "locations" }); listBuildings = (List<Building>)serializer.Deserialize(reader); return listBuildings; } } 
+6
source share
5 answers

Try the following:

 [XmlRoot("locations")] public class BuildingList { public BuildingList() {Items = new List<Building>();} [XmlElement("location")] public List<Building> Items {get;set;} } 

Then deserialize the entire BuildingList.

 var xmlSerializer = new XmlSerializer(typeof(BuildingList)); var list = (BuildingList)xmlSerializer.Deserialize(xml); 
+6
source

I know this is an old question, but today I struggled with it and found an answer that does not require encapsulation.

Assumption 1: You have control over the original Xml and its construction.

Assumption 2: You are trying to serialize Xml directly to a List<T> object

  • You must specify the Root element in Xml as ArrayOfxxx , where xxx is the name of your class (or the name specified in XmlType (see 2.))
  • If you want your xml Elements to have a different name for the class, you should use XmlType in the class.

NB: If your type name (or class name) begins with a lowercase letter, you must convert the first character to uppercase.

Example 1 - Without XmlType

 class Program { static void Main(string[] args) { //String containing the xml array of items. string xml = @"<ArrayOfItem> <Item> <Name>John Doe</Name> </Item> <Item> <Name>Martha Stewart</Name> </Item> </ArrayOfItem>"; List<Item> items = null; using (var mem = new MemoryStream(Encoding.Default.GetBytes(xml))) using (var stream = new StreamReader(mem)) { var ser = new XmlSerializer(typeof(List<Item>)); //Deserialising to List<Item> items = (List<Item>)ser.Deserialize(stream); } if (items != null) { items.ForEach(I => Console.WriteLine(I.Name)); } else Console.WriteLine("No Items Deserialised"); } } public class Item { public string Name { get; set; } } 

Example 2 - With XmlType

 class Program { static void Main(string[] args) { //String containing the xml array of items. //Note the Array Name, and the Title case on stq. string xml = @"<ArrayOfStq> <stq> <Name>John Doe</Name> </stq> <stq> <Name>Martha Stewart</Name> </stq> </ArrayOfStq>"; List<Item> items = null; using (var mem = new MemoryStream(Encoding.Default.GetBytes(xml))) using (var stream = new StreamReader(mem)) { var ser = new XmlSerializer(typeof(List<Item>)); //Deserialising to List<Item> items = (List<Item>)ser.Deserialize(stream); } if (items != null) { items.ForEach(I => Console.WriteLine(I.Name)); } else Console.WriteLine("No Items Deserialised"); } } [XmlType("stq")] public class Item { public string Name { get; set; } } 
+3
source

You do not know how Building corresponds to the location that you have in your xml, but for me it makes sense if they are named the same. Instead of using a list, use a LocationList and it becomes:

 [Serializable()] [XmlRoot("locations")] public class LocationCollection{ [XmlElement("location")] public Location[] Locations {get;set;} } [Serializable()] [XmlRoot("location")] public class Location { [XmlElement("id")] public int LocationID { get; set; } [XmlAttribute("locationtype")] public string LocationType {get;set;} [XmlElement("name")] public string Name { get; set; } [XmlElement("description")] public string Description { get; set; } [XmlElement("mubuildingid")] public string MUBuildingID { get; set; } } 

You can then deserialize as follows:

 var request = WebRequest.Create(method) as HttpWebRequest; var response = request.GetResponse() as HttpWebResponse; var streamReader = new StreamReader(response.GetResponseStream()); TextReader reader = streamReader; var serializer = new XmlSerializer(typeof(LocationCollection), new XmlRootAttribute() { ElementName = "locations" }); var listBuildings = (LocationCollection)serializer.Deserialize(reader); return listBuildings; 
+2
source

I know the old question, but ran into it, faced with a similar problem. Based on @ricovox's answer and in the context of the OP question, this is the model I would use to serialize its xml:

 [Serializable, XmlRoot("locations")] public class BuildingList { [XmlArrayItem("location", typeof(Building))] public List<Building> locations { get; set; } } [Serializable] public class Building { public int LocationID { get; set; } public string Name { get; set; } public string Description { get; set; } public string MUBuildingID { get; set; } public List<Building> GetAll() { ... } } 

The OP error was to create a list item as root

0
source

Use [XMLArray] for collection properties.

-1
source

Source: https://habr.com/ru/post/952246/


All Articles