[Serializable] and ISerializable
Eagle-eyed readers will have noticed that in all the preceding
examples the classes are sealed.
This is no
accident. Marking a class as [Serializable]
and
deciding to whether to implement ISerializable
has
some specific implications for both base and derived types, and
deserves separate discussion.
Consider the following serializable class hierarchy:
[Serializable] public class Person { public string Name; public int Age; // Rest of class... } [Serializable] public sealed class Student: Person { public string Course; // Rest of class... }
In this example both Person
and Student
are
serializable, and both classes use the default runtime serialization behavior
since neither class implements ISerializable
.
Now imagine that the developer of Person
decides
for some reason to implement ISerializable
and provide
a deserialization constructor to control Person
serialization.
The new version of Person
might look like this:
[Serializable] public class Person : ISerialization { public string Name; public int Age; public void GetObjectData(SerializationInfo si, StreamingContext sc) { si.AddValue("IChangedTheNameFieldName", Name); si.AddValue("IChangedTheAgeFieldName", Age); } protected Person(SerializationInfo si, StreamingContext sc) { Name = si.GetString("IChangedTheNameFieldName"); Age = sc.GetInt32("IChangedTheAgeFieldName"); } // Rest of class... }
Although this works for instances of Perso
n,
this change breaks serialization of Student
instances. Serializing ...
Get C# in a Nutshell now with the O’Reilly learning platform.
O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.