LLVM 3.0 Type System Rewrite
blog.llvm.org
blog.llvm.org
When you have run-time type information (RTTI) in a language it turns out that having names for types is important, for data serialization in particular. But when you also have anonymous types (as Delphi does), you can end up with versioning problems, because you need to generate names for these things - and they usually end up involving numbers of some kind.
So you can see a type that looks like this:
type
R = record
X: record
E: set of (a, b);
end;
end;
Only R has a name; the names of the types of the field R.X, and the field R.X.E, etc. are anonymous and end up being something like ':1', ':2' etc. But change the order of declarations and you change the numbering. So probably the most robust option is a name generated from the structure of the type, a bit like a mangled C++ signature.But when it comes time to serialize, the effort to map all the properties and relationships into an enumerated form can very quickly invade the codebase and dominate it like a lodestone. Either you "bash down" the most structured elements into more primitive forms so that version compatibility is maintained(leading you to code in a primitive style as well), or you escalate to the prospect of storing code as well as data(the "image" strategy).
For example, "transparent" serialization really isn't because you get run into severe versioning issues. But dropping to primitives doesn't work well either, because then there's impedance to deal with. If you acknowledge there is bound to be impedance, you can encapsulate it in a separate mapping/specification, and deal with it on its own terms.
That lets you do things like evolve your storage format and internal model independently, without the very real drawbacks of an image-style system.
1. By doing reflective magic (potentially a lot of it) at the moment of serialization so that a serialization-friendly form can be teased out. If you are not working within a reflective environment, this option doesn't exist without additional effort. And if the runtime changes the magic breaks.
2. By "primitivizing" the runtime so it's closer to the serialized representation, at the expense of dirtying the codebase to exchange e.g. object references for id numbers. You can make it look prettier again by enforcing conventions, but the extra weight is still there. Adding reflection within an environment that didn't have it built-in also requires going through this step.
Those two options are the design tradeoff. And the bigger your serialization ambitions go the more the pressure builds to either massively primitivize(e.g. use a SQL database for all data and make the special runtime representations non-persistent always) or make an image so that data never "actually" leaves the runtime.
In electing to use a database layer everywhere, web apps have more-or-less standardized on primitive designs, and subsequently try to claw back readable code through tricks like ORMs and DSLs.