Re: Vertical inheritance with a non-abstract superclass
Re: Vertical inheritance with a non-abstract superclass
- Subject: Re: Vertical inheritance with a non-abstract superclass
- From: David Avendasora <email@hidden>
- Date: Mon, 10 Mar 2008 16:51:38 -0400
On Mar 10, 2008, at 3:43 PM, David Elliott wrote:
On Mar 10, 2008, at 11:35 AM, David Avendasora wrote:
Nathan,
I think you will find that Vertical Inheritance is much more
resource intensive than you'd think. David Elliotts email points
this out in that if query an object of the superclass or any one
subclass is requested, it does a query for each possible subclass
as well. So if you have 3 subclasses, it will do 4 queries, even if
you are only trying to instantiate one of the subclasses, or even
if you are just trying to instantiate the superclass.
Woah. Hold up there. If you fetch one of the subclasses you will
see one query. It will join the subclass table with the base
table. That's it.
It's only when you fetch the base abstract class that EOF must
necessarily use one query for each subclass. That is, after all,
the entire point of vertical inheritance.
Huh, I swear it would always grab everything for each subclass which
confused me at the time because, as you said, that is the entire point
of VI, but when I watched the SQL, I was sure that it went and queried
everything. I can't check now as I left VI behind a while ago. I'll
take your word for it though.
With single-table inheritance, if you are loading the superclass,
even though the query may bring back all the fields for all the
subclasses as well, it does it in one DB operation, that is going
to be much less overhead than what VI does.
To me, Vertical Inheritance should be viewed as something to use
when you are trying to make use of data in a legacy database, not
as a tool for designing a new database.
Vertical inheritance has its place. I think a lot of people on this
list and even writing the literature have a tendency to discount
it. That said...
Also, because of the way WO uses faults, what you are trying to
avoid likely isn't even a problem in the first place.
If the only reason you are using Inheritance in this situation is
to split off attributes that aren't required, then I think you're
going to want to really reconsider using Inheritance at all.
As far as making it work across models, is this a new project or an
existing one? It sounds like you are trying to implement many of
the more complicated EOF concepts in a new project.
The biggest problem with vertical inheritance or really any sort of
inheritance in EOF is that it necessarily complicates your model.
That said, if your data model really does have a vertical-
inheritance structure to it and you really think that's the best way
to model it, then you OUGHT to model it that way.
The biggest mistake with EOF inheritance is to use it purely for
polymorphism. If you use it because you really do want additional
attributes in the subclasses then you're doing it right. But keep
in mind that once you create an object of a given class there is no
converting it to another class. If your data model requires that
you be able to change some property (e.g. attribute or even a to-one
relationship) of an object and have it magically change classes then
you are definitely modeling it wrong.
If D2W is involved, inheritance of any sort can be somewhat of a
pain, particularly in the case of owned to-many relationships to the
abstract base class. At one time I implemented a quick hack that
simply changes the new button to jump to a little dialog-like page
where the user must select the subclass.
This does however bring up yet another point. Do NOT use inheritance
if the only commonality in the data-model between your subclasses is
that they are owned by the same object (i.e. they have a to-one
pointing back to their owning object). And still don't use it if
the only commonality is a handful of attributes and to-one
relationships. In that case you can very likely have a separate to-
many from your owning object to each type. You may as well model it
this way because ultimately that's exactly what EOF is doing.
You may in this case have some attribute common to all like a
totalAmount (e.g. a cost or price). And in that case you may be
better off taking advantage of the fact that
valueForKey("totalAmount") works regardless of the type of object so
long as it has key value coding. And if you want to do
totalAmount() then possibly define yourself an interface with that
in it. You can synthesize a to-many relationship to an array of
this interface or of EOGenericRecord by simply concatenating all of
the real to-many relationships. You can even go as far as to
synthesize a setter and add/remove object methods if these help you
programmatically work with your model.
But again, it all boils down to one simple fact: Do not use
inheritance for YOUR benefit. Find a different way to get
polymorphic behavior. Recognize that KVC effectively makes every
property its own interface (because valueForKey("foo") or
takeValueForKey(bar, "foo") works on any object with that property.
This is ultimately a watered-down version of an Objective-C truism.
Namely that every method selector effectively implicitly defines its
own interface with exactly one method.
You know, it's simple things like these that when I read them I wonder
why I didn't think of them.
Use inheritance when the data model demands that you do. Never
because you think it's going to make your life easier. In the end
it will not unless you have hit that one very special case where the
data model does demand that you use it and then it will make your
life a whole lot easier. If your data model doesn't demand it, it
will make your life a whole lot harder. Recognizing what does and
doesn't demand it is the difficult part. It's one of those hard
choices you have to make.
Make it work. Then make it work right. THEN make it work fast.
This is actually an argument for vertical inheritance, not against
it. Make it work often means using vertical inheritance. Make it
work right can be re-evaluating whether inheritance of any sort is
actually appropriate. Make it work fast can mean deciding to do
single-table or horizontal inheritance to improve your speed if you
really have to.
Good point.
That said, vertical inheritance really is the cleanest data model of
all the inheritance types so don't shy away from using it when it
really is appropriate.
Maybe I should place the blame where it belongs. MS SQL. Without
deferred constraints, it made VI a nightmare as WO would try to insert
the subclass first and then choke on the fact that the PK of the one-
to-one relationship didn't exist. Chuck Hill has some stuff in
ERExtensions to resolve this but they came just as I decided to write
it off.
-Dave
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Webobjects-dev mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden