Tom
Tom

Reputation: 57

Cant serialize a list of objects (each object contain a list) to xml

Im trying to understant how serialize works, but I have been stuck on a problem a while now.

What im trying to do is that I have a manager that handle a list of object. In this case recipe´s. In each recipe there is a list of ingredients. My manager is derived from a Listmanager class. The list of ingredients also uses the List manager class.

I have used this when I serialized a similar manager, except I serialized to binary (.dat). That worked and even worked with deserialize. I know xml is a bit different, but still worth mentioning..

The problem --> All I get is this when I serialize:

<?xml version="1.0"?>
<RecipeManager xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" />

I would like the xml-document to resemble something like this:

<Recipe>
<Name>Food<Name>
<Ingredient>blabla<Ingredient>
<Ingredient>blabla2<Ingredient>
<Ingredient>blabla3<Ingredient>
</Recipe>

This is my Listmanager, it has a bunch of other methods but this just so you can get an idea of how it looks:

[Serializable]
    public class ListManager<T> : IListManager<T>
    {
        private List<T> list;

        public ListManager()
        {
            list = new List<T>();
        }
        public int Count { get { return list.Count; } }

        public void Add(T aType)
        {
            list.Add(aType);
        }

        public bool ChangeAt(T aType, int index)
        {
            if (CheckIndex(index))
            {
                list[index] = aType;
                return true;
            }
            else
            {
                return false;
            }
        }
        /// <summary>
        /// Tittar så det finns ett objekt på platsen som användaren valt
        /// </summary>
        /// <param name="index"></param>
        /// <returns></returns>
        public bool CheckIndex(int index)
        {
            if (index < 0)
            {
                return false;
            }
            else if (list[index] != null)
            {
                return true;
            }
            else
                return false;
        }

This is my RecipeManager class:

[Serializable]
    public class RecipeManager : ListManager<Recipe>
    {
        /// <summary>
        /// Konstruktor
        /// </summary>
        public RecipeManager()
        {
            TestData();
        }

        private void TestData()
        {
            Recipe testInfo = new Recipe();

            testInfo.Name = "AnimalSuperFood";
            testInfo.IngredientsList.Add("2dl of water");
            testInfo.IngredientsList.Add("3g of meat");
            testInfo.IngredientsList.Add("1ml of lemon");
            Add(testInfo);
        }
    }

This is my recipe class:

[Serializable]
[XmlRoot("Recipe")]
public class Recipe
{
    #region props
    private ListManager<string> ingredientsList;

    [XmlArray("Ingredient")]
    public ListManager<string> IngredientsList
    {
        get { return ingredientsList; }
    }

    private string name;
    public string Name
    {
        get { return name; }
        set { name = value; }
    }
    #endregion
    /// <summary>
    /// Konstruktor
    /// </summary>
    public Recipe()
    {
        ingredientsList = new ListManager<string>();
    }
    public override string ToString()
    {
        string strOut = string.Format("{0}: ", Name); ;
        for (int i = 0; i < IngredientsList.Count; i++)
        {
            if (i != (IngredientsList.Count - 1))
            {
                strOut += string.Format("{0} mixed with ", IngredientsList.GetAt(i));
            }
            else
            {
                strOut += string.Format("{0}", IngredientsList.GetAt(i));
            }
        }
        return strOut;
    }
}

This is where i send my manager that contains the objects:

using (SaveFileDialog dlg = new SaveFileDialog())
            {
                dlg.Title = "Save xml file";
                dlg.Filter = "xml file (*.xml)|*.xml";
                if (dlg.ShowDialog() == DialogResult.OK)
                {
                    try
                    {
                        SerializationUtility.XmlFileSerialize(recipeMgr, dlg.FileName);
                        MessageBox.Show("Save succesful", "Success", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    }
                    catch (Exception ex)
                    {
                        MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Information);
                    }
                }

            }

And last this is where i serialize:

  public static void XmlFileSerialize<T>(T obj, string filePath)
        {
            using (Stream s = new FileStream(filePath, FileMode.Create, FileAccess.Write))
            {
                XmlSerializer xmlWriter = new XmlSerializer(typeof(T));
                xmlWriter.Serialize(s, obj);
            }
        }

And last but not least, please explain why my question was bad if you Think so. dont just vote down and leave.. I am trying to learn.. thanks!

Upvotes: 0

Views: 149

Answers (1)

Gusman
Gusman

Reputation: 15161

Ok, found your problem after re-reading the code: Any property you want to be serialized must be public.

Your "list" on ListManager is private, so it will not be serialized and there will be nothing.

Make it public and it will work.

Also any other private property/field you want to serialize must be public.

Upvotes: 2

Related Questions