Beefy Boxes and Bandwidth Generously Provided by pair Networks Joe
good chemistry is complicated,
and a little bit messy -LW
 
PerlMonks  

Re^5: OO-style modifiers for 'sub' ?

by dpuu (Chaplain)
on Feb 01, 2003 at 00:37 UTC ( #231768=note: print w/ replies, xml ) Need Help??


in reply to Re^4: OO-style modifiers for 'sub' ?
in thread OO-style modifiers for 'sub' ?

OK, I'll admit that I went of at a bit of a tangent there. But since we're here, let me refute your example: an interface named "PitchControl" would be no less ambiguous than a method named "set_pitch". We can't use the ambiguity argument to support explicitly named interfaces.

But you are right. The discussion shouldn't be about whether it is valid to infer an interface from the body of the implementation of a client (a la templates): its about whether it is valid to infer an interface from the functions supported by an object. That is: we're talking about the dependency structure:

interface Foo { method fn (...); } class Bar : isa Foo { method fn (...) {...} }
Vs
class Bar { method fn (...) {...} } interface Foo { require method fn (...); }
The second example states that an object implements the interface if it supports a specific set of methods. It says: "if it looks like a duck, and quacks like a duck, and walks like a duck: then lets assume that it is a duck".

In both cases, the interface is made explicit. Client code can be written to require an object that implements a specific interface: the interface is explicit from the client's point of view. The binding between the object and the interface is also explicit, but the direction of the dependency is different.

But your original question still stands: why would we want to break the explicit dependency between the class definition and an interface?

Imagine you have a blob of 3rd party code that has an overly fat interface. You can't modify this code (e.g. you're not sysadmin). You want to use these blobs in you own code, which uses a much thinner version of the same interface. You want to validate your input (i.e. does the input object implement your thin interface) without modifying the source code of an object that implements the fat interface.

fanfare: Inferred Interfaces to the rescue! --Dave


Comment on Re^5: OO-style modifiers for 'sub' ?
Select or Download Code
Re^6: OO-style modifiers for 'sub' ?
by adrianh (Chancellor) on Feb 01, 2003 at 22:16 UTC
    OK, I'll admit that I went of at a bit of a tangent there. But since we're here, let me refute your example: an interface named "PitchControl" would be no less ambiguous than a method named "set_pitch". We can't use the ambiguity argument to support explicitly named interfaces.

    Sorry - obviously wasn't being clear. I wasn't proposing a PitchControl interface. I was just pointing out that the method name isn't enough. The method would be part of the "interfaces" of MusicalInstrument and Aircraft, which are not ambiguous.

    In both cases, the interface is made explicit. Client code can be written to require an object that implements a specific interface: the interface is explicit from the client's point of view. The binding between the object and the interface is also explicit, but the direction of the dependency is different.

    I think we have different definitions of "interface". To me it includes the implied contract of the class, so:

    interface Aircraft { method set_pitch (...); } class Jet : isa Aircraft { method set_pitch (...) {...} }

    is saying a very different thing from:

    class Jet { method set_pitch (...) {...} } interface FlyingThings { require method set_pitch (...); }

    since:

    class Piano { method set_pitch (...) {...} }

    isn't an Aircraft, but is a FlyingThing.

    Imagine you have a blob of 3rd party code that has an overly fat interface. You can't modify this code (e.g. you're not sysadmin). You want to use these blobs in you own code, which uses a much thinner version of the same interface. You want to validate your input (i.e. does the input object implement your thin interface) without modifying the source code of an object that implements the fat interface.

    Dealing with code you can't alter is once case where I can see it being useful (as I briefly mentioned in another thread).

    That's one way of doing it certainly. But the information that ThinInterface is a subset of ThickInterface is lost. All you are saying is that they have the same method names - not that those methods do the same "things" to the same kind of objects.

    While it might be a useful hack - that's what it is. You are deliberately subverting the isa hierarchy because you can't express the relationship that you want to express directly. It's something that should be used very carefully since it subverts (in my opinion) what OO is all about.

    There are also other ways of getting round the problem. For example, if you have multiple inheritance you could declare a subclass ThickThin of ThickInterface that isa ThinInterface, and use the subclass where you would have used ThickInterface objects.

    ThickInterface ThinInterface \ / ThickThin

    With perl you can do even do ghastly things like:

    unshift @ThickInterface::ISA, 'ThinInterface';

    to make ThickInterface a ThinInterface retrospectively :-)

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: note [id://231768]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others scrutinizing the Monastery: (23)
As of 2014-04-17 15:52 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    April first is:







    Results (453 votes), past polls