From: Tim.Hunter@... Date: 2002-09-13T22:23:14+09:00 Subject: Re: not grasping the method overloading/multi-dispatch thing On Fri, 13 Sep 2002 07:01:51 GMT, "Gavin Sinclair" wrote: > >----- Original Message ----- >From: > > >> In Phil's example, it seems like "meth" is testing the argument's >> class, not its type. According to my copy of _Design Patterns_, the >> type of an object is the set of methods to which it can respond. If >> two objects respond to the same set of methods then they have the same >> type, even if they aren't objects of the same class. > >This is a bit idealised. If two objects implement the same methods (rather, >the same method *names*), but completely different and unrelated behaviour, >..? Well, if you passed the wrong object to a method expecting the other object, that would be a bug. But why would you write or use code that did this? > >> For me, testing an argument's class is a code smell. What do I care if >> "s" is a Foo or a Bar, as long as it responds to the methods I need to >> send it? I try to design my classes and methods so that, if I want >> method "A" to accept as arguments objects that are created from >> different classes, then each of the classes should implement the set >> of methods that "A" will send. As far as "A" is concerned, all the >> objects have the same type. > >Your second paragraph uses a narrower definition of "type" than your first. >The first was that objects A and B respond to *all* the same methods. The >second holds that A and B need only respond to the methods that method M wants >to use. > That's correct. Again, _Design Patterns_ says "An object can have many types." Different methods can use different interfaces. All that matters is that the object has the interface - that is, it responds to the set of methods - that the method sends. >Going with the second definition, there's no need, then, to test for explicit >class with is_a? or kind_of?; you can say: > > class C > method M(x, y) > fail TypeError unless x.respond_to? :foo and y.respond_to? :foo > ... > end > end What about just letting Ruby handle it, instead? class C def method(x,y) x.foo y.foo end end If x or y doesn't respond to :foo, then Ruby will raise a TypeError for you. Insert rescue blocks as necessary. > >(Of course, y may "respond" to :foo only by implementing #method_missing, but I >won't go there...) If it does, AND that's not the right behavior, then you've got a bug in your code. > (snip) > >What I'm trying to say is that if you want to demonstrate that type is nothing >more than a set of strings (representing method names), then implementing >"concat" is not a sufficiently strong example. Well, I'm not so much asserting it as I'm passing along "received wisdom" from the Gang of Four. Plus, it seems to me that Ruby's implementation - typeless variables, "to_type" methods - supports this statement.. > >Experience alone is enough to decide these things one way or the other, but I >find that, at critical parts of application code, testing the explicit class of >an object can be quite reassuring. Of course, sometimes I just check >respond_to?, and most of the time I damn the torpedos and don't check anything >:) > >Cheers, >Gavin >