RE: Subclassing with more restrictive initializers
RE: Subclassing with more restrictive initializers
- Subject: RE: Subclassing with more restrictive initializers
- From: Andy Klepack <email@hidden>
- Date: Wed, 25 Feb 2009 09:56:55 -0800
- Acceptlanguage: en-US
- Thread-topic: Subclassing with more restrictive initializers
Ah, it looks like I'm in good company :)
Thanks for the references!
-Andy
-----Original Message-----
From: Andy Lee [mailto:email@hidden]
Sent: Wednesday, February 25, 2009 9:16 AM
To: Andy Klepack
Cc: email@hidden
Subject: Re: Subclassing with more restrictive initializers
This is a variation of the Square-Circle problem, aka Circle-Ellipse:
<http://www.google.com/search?q=square+rectangle+inheritance>
<http://www.google.com/search?q=circle+ellipse+inheritance>
<http://en.wikipedia.org/wiki/Circle-ellipse_problem>
You have a class that conceptually is a refinement of another class,
which typically suggests a class-superclass relationship. The problem
is that the subclass would have to disallow some behavior that is
promised by the contract of the superclass. For example, in human-
speak, a Square "is a" Rectangle, but in OO-speak, you could
reasonably have a method -[Rectangle initWithWidth:height:] but it
wouldn't make sense for Square. To use your example, a PreferenceFile
"is a" File, but it wouldn't make sense for it to respond to -
initWithPath:.
The Wikipedia article linked above lists some approaches to the
problem. One approach that comes to mind -- use a class cluster -- is
a variation of the "Limit the interfaces" option.
--Andy
On Feb 25, 2009, at 11:39 AM, Andy Klepack wrote:
> I've run up against this situation more than once and I'd be
> interested in any opinions and best-practices out there.
>
> I have a class that has one or more initializers that accept
> parameters. The class also has behavior.
>
> I want to implement a second class that has the behavior of the
> first in addition to its own behavior. This class should also have
> more restrictive initializers. That is, the second class should not
> allow the kind of parameterization that the first class does.
>
> On the one hand this feel a like inheritance: the second class
> really is-a kind of the first class. But those pesky initializers
> (from the first class) don't make sense for the subclass.
>
> On the other hand, this looks kinda like trying to create an
> instance through sub-classing (and that would be wrong) except that
> behavior is being added as well.
>
> On the other-other hand this feel like it could be composition
> (instances of the second class have-a member of the first class),
> but the behavior of the first class would have to be accessed
> through a wrapper provided by the second class.
>
> To make things more concrete (this isn't the actual case I've run
> into, but it's a similar, simpler illustration) consider a class
> "File" that has an initializer 'initWithPath:' and behavior
> 'delete', 'rename', etc. Then consider wanting to implement a class
> like 'PreferenceFile' that should only refer to files in the
> Preferences directory and thus has an 'initWithName:" initializer.
> "initWithPath" provides too much parameterization since it could
> refer to any file outside of the Preferences directory. Finally, the
> PreferenceFile class should have the same behavior as File and add
> some of its own (e.g. "setPrefValue:ForKey:").
>
> Should PreferenceFile inherit from File despite the initialize
> behavior being undesirable? Is composition somehow more appropriate?
> Is this confusion the result of thinking about the problem from the
> wrong direction?
>
> Any advice about how to think about and approach this sort of design
> problem would be great.
>
> -Andy
aglee
_______________________________________________
Cocoa-dev mailing list (email@hidden)
Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden