4

I have class Animal and classes Dog and Cat inheriting from it. Class Animal has property X. I would like to generate XML for "Dog" without "X" property and for "Cat" with "X" property. XmlIgnore doesn't work here in the way I expected.

I tried to use virtual property and then override it in derived class but it didn't work.

class Program
{
    static void Main(string[] args)
    {
        Dog dog = new Dog();
        Cat cat = new Cat();

        SerializeToFile(dog, "testDog.xml");
        SerializeToFile(cat, "testCat.xml");
    }

    private static void SerializeToFile(Animal animal, string outputFileName)
    {
        XmlSerializer serializer = new XmlSerializer(animal.GetType());

        TextWriter writer = new StreamWriter(outputFileName);
        serializer.Serialize(writer, animal);
        writer.Close();
    }
}
public abstract class Animal
{
    public virtual int X { get; set; }
}
public class Dog : Animal
{
    [XmlIgnore]
    public override int X { get; set; }
}
public class Cat : Animal
{
    public override int X { get; set; }
}
Zygmuntix
  • 339
  • 3
  • 13
  • what do you want to achieve? – LuckyLikey Apr 10 '19 at 15:35
  • @LuckyLikey I want to by default generate XML with "X" value for classes inheriting from Animal. But for Dog class I want to generate XML without "X" (because of XmlIgnore attribute). – Zygmuntix Apr 11 '19 at 09:03
  • @LuckyLikey I modified my question to be more clear. – Zygmuntix Apr 11 '19 at 10:31
  • yes, but what's the reason to do that? Just out of curiosity. – LuckyLikey Apr 17 '19 at 05:26
  • @LuckyLikey My team leader told me to make a research about this. But then I talked with him again and it turned out that we misunderstood each other... (this was not exactly the task I had to do). – Zygmuntix Apr 19 '19 at 13:33
  • hehe.. how to research ;-) Well, as this approach doesnt work, i guess you'd have to implement this behavior yourselv, by customizing the `XmlSerializer`. But I think you're done with this anyway. Cya around. – LuckyLikey Apr 24 '19 at 14:15

1 Answers1

0

Even though you don't need this anymore, I still found the solution to this problem.

You can create XmlAttributeOverrides and set the XmlAttributes.XmlIgnore Property for certain fields of classes.

private static void SerializeToFile(Animal animal, string outputFileName)
{
    // call Method to get Serializer
    XmlSerializer serializer = CreateOverrider(animal.GetType()); 
    TextWriter writer = new StreamWriter(outputFileName);
    serializer.Serialize(writer, animal);
    writer.Close();
}

// Return an XmlSerializer used for overriding.
public XmlSerializer CreateOverrider(Type type)
{
    // Create the XmlAttributeOverrides and XmlAttributes objects.
    XmlAttributeOverrides xOver = new XmlAttributeOverrides();
    XmlAttributes attrs = new XmlAttributes();

    /* Setting XmlIgnore to true overrides the XmlIgnoreAttribute
     applied to the X field. Thus it won't be serialized.*/
    attrs.XmlIgnore = true;
    xOver.Add(typeof(Dog), "X", attrs);

    XmlSerializer xSer = new XmlSerializer(type, xOver);
    return xSer;
}

Of course you can also do the opposite by setting attrs.XmlIgnore to false.

Check this out for more information.

LuckyLikey
  • 3,504
  • 1
  • 31
  • 54