- Home /
Serialization of inherited classes, could this work?
Hello, I think I have come up with a way to serialize inherited classes with the new ISerializationCallbackReceiver class, but I dont know if I am missing something, so I figured I would ask the community if there is more to this. If I have this child class
[Serializable]
public class ParentClass
{
[SerializeField]
protected byte[] serializedData;
}
[Serializable]
public class ChildClass : ParentClass
{
[SerializeField]
Vector3 extraData;
}
and it is attached to a gameobject like so
public class AttachedBehavior : Monobehavior, ISerializationCallbackReceiver
{
[SerializeField]
ParentClass[] parentClassArray;
void Awake()
{
parentClassArray = new ParentClass[2] {new ChildClass(), new ChildClass()};
}
public void OnBeforeSerialize()
{
parentClassArray[0].serializedData = parentClassArray[0].ObjectToByteArray();
parentClassArray[1].serializedData = parentClassArray[1].ObjectToByteArray();
}
public void OnAfterSerialize()
{
parentClassArray[0] = parentClassArray[0].serializedData.ByteArrayToObject();
parentClassArray[1] = parentClassArray[1].serializedData.ByteArrayToObject();
}
}
and finally, here is the code for the extensions:
public static class Extensions
{
public static byte[] ObjectToByteArray(this Object obj)
{
if (obj == null)
return null;
BinaryFormatter bf = new BinaryFormatter();
MemoryStream ms = new MemoryStream();
bf.Serialize(ms, obj);
return ms.ToArray();
}
// Convert a byte array to an Object
public static Object ByteArrayToObject(this byte[] arrBytes)
{
MemoryStream memStream = new MemoryStream();
BinaryFormatter binForm = new BinaryFormatter();
memStream.Write(arrBytes, 0, arrBytes.Length);
memStream.Seek(0, SeekOrigin.Begin);
Object obj = (Object)binForm.Deserialize(memStream);
return obj;
}
}
My thought is that the byte array would get serialized, even if we lose the child data. But, when it gets deserialized, it gets turned back into an object stream and converted into a child object again, meaning you get your data back. Could this work? I tested it on my machine and got the correct results, but it was a simple test.
It could work, but really, it's kind of sketchy, and tedious to have to do for every object you have, so it must be automated somehow. Not to mention unless you're using surrogates, this will not work with Unity objects, cause you're using BinaryFormatter and unity objects are not marked with Serializable. If you're interested in better/advanced serialization features, check out VFW
I think it looks like an elegant solution to me. Vexe's VFW is definitely more robust, however I$$anonymous$$HO, overly so. It's comprehensiveness makes it very complex and confusing. He pretty much rewrote the whole unity serialization system, where, you're just working around one particular issue, polymorphic serialization. I'd like to know if you test this more thoroughly as I might take a similar approach in my project.
I do have one issue with your approach... if you're ParentClass has some fields like, lets say, an array of Vector3 (Vector3[]), you would be serializing that into your byte array unnecessarily as it is inherited by all derived classes and is already properly serialized by Unity. That might not be a big deal but if the base class has all the heavy data and the derived class is light-weight, you're doing a lot of extra work.
I did run into that issue when I was working with it. And to answer your question, yes this does work for polymorphic serialization. Unfortunately though, it didnt work in my case because I had too many objects and caused an out of memory exception when Unity Serialized my world.
Your answer
Follow this Question
Related Questions
Google Cloud Save Data returns empty. 1 Answer
Scriptable Object List values are always null 1 Answer
An OS design issue: File types associated with their appropriate programs 1 Answer
Wrong serialization when using ScriptableObject + [System.Serializable] + inheritance 2 Answers
Serialization and Inheritance: Great-GrandChild Class appears unserialized 0 Answers