So… I can sort of understand the pedantry in regards to kurt saying “even private field (variable) values are serialized by default” if only because it can be easily confused to mean serialized to disk. Which it is not serialized to disk. But I would also be willing to not nitpick because I get what he’s saying.
But if we’re going to be pedantic.
Well:
They are unloaded and reloaded. Or SOMETHING is happening that could be described with the terms ‘loaded’ and ‘serialized’.
We can check the object every time you start the game by simply reading its address, instance id, and header hash.
The address and instance id remains the same. BUT the header hash (using something like RuntimeHelpers.GetHashCode will create a hash based on the header of the object in memory at the address of the object) will be different between starts.
This means that an entire new object has been placed into memory at the same address of the previous object from previous play session.
Of course… now we’re getting into the gritty details of what makes a new object a new object. Is it actually new if it’s at the same address and any and all references therefore inherently synced to this new object making it appear like it hasn’t changed down to its instanceid and address being identical. Is it new if the C++/internal object may or may not have been altered.
But it’s not identical, because 1) the header has changed and 2) its entire state isn’t necessarily maintained (and state is sort of the entire point of object identity) since fields that can’t be serialized aren’t maintained.
And to note, we know some sort of serialization is definitely occurring. Serialization doesn’t necessarily mean it has to be to disk. Serialization is just the creation of a byte stream out of an object. That byte stream can be stored to disk, transmitted over network, moved between memory spaces, or any number of things.
But we know it’s serialized for a few reasons:
-
the ISerializationCallbackReceiver interface will fire both of its events on play. The ‘before’ just before the transition to play, and ‘after’ as play enters.
-
marking things System.NonSerialized gets ignored and will reset as if they were initialized by the constructor
-
types that the Unity serialization engine doesn’t support (like Dictionary or HashSet) are ignored as well.
So clearly unity is utilizing the same serialization logic that they use else where during this process. But they’re including private fields that aren’t otherwise marked nonserialized explicitly or can’t be by said logic.
I guess this may or may not be considered ‘unloaded/loaded’… but that’s more to do with the nebulous definitions of those words since they’re not explicitly defined in the context. Which is the same cloudy nature of the phrase ‘serialize’ since depending context they can imply different things.
TLDR; it’s kind of pedantic at this level of discussion.
The point still stands… state is maintained between play except for things that can’t be serialized (nonserialized, or just outright can’t because its unsupported).
As kurt said: “Hmmm… I can’t decide if we’re agreeing or disagreeing. Heh…”