6 ms·
The Gang of Four is Wrong and You Don't Understand Delegation
- sirfried 14y agohe's just selling a book, relax
- jonathanyc 14y agoSo he's redefining delegation in your own sense (implied by his strange titlebait "The Gang of Four is Wrong") and then criticizing everyone else post hoc? I fail to see how this deserves any upvotes.
- saturnflyer 14y agoI'm the author. I'm not redefining delegation. I'm pointing out that the Gang of Four, who cited Henry Lieberman who created the term, described it incorrectly. You can read the citations in the Design Patterns book and see exactly what they got wrong. Here's a link to Lieberman's work http://web.media.mit.edu/~lieber/Lieberary/OOP/Delegation/Delegation.html http://web.media.mit.edu/~lieber/Lieberary/OOP/Delegation/De...
- nateberkopec 14y agoIf both definitions of 'delegation' end up having the same purpose, does it really matter? Why should I care that Rails' 'delegate' isn't exactly how some guy in 1970 would've written it? This whole "object-orientation" bent in the Ruby community lately just feels like a crusade, with people thumping on old OO books, each proclaiming theirs is the "true way". And, usually, like in this example, it doesn't even matter because their code ends up doing exactly the same thing with little real-world gains in readability or ease of understanding.
- dasil003 14y agoOne of the traits that allows us to be competent programmers is a pedantry about technical terminology. Why overload the concept of message forwarding with a second term if what that term was originally coined to describe is a useful paradigm? I had never heard of this distinction, however it immediately made sense to me because I've run into this case in Ruby where using a ruby "delegate" object actually was much more verbose than I had envisioned because of all the context I had to bring over to the delegate object one way or another. In the event I decided "delegation" was not right because the implementation necessarily violated the Law of Demeter. So yeah I think pragmatically it does matter.
- true_religion 14y ago> One of the traits that allows us to be competent programmers I think we've failed then since we've totally overloaded and confused basic concepts such as weak/strong typing and dynamic/static typing. To make matters worse, those are cases where we as programmers invented to terminology at hand and didn't just appropriate it into a programming context.
- petercooper 14y agoSince you brought up typing, you might enjoy this related confusion: http://stackoverflow.com/questions/9154388/does-untyped-also-mean-dynamically-typed-in-the-academic-cs-world http://stackoverflow.com/questions/9154388/does-untyped-also...
- btilly 14y agoI agree that there are cases where pedantry is necessary for programmers. That does not mean that pedantry is necessarily valuable. In this case a distinction is being drawn that would make "delegation" mean something that is worse from the point of view of good software design, which would leave the thing that is better software design without its commonly understood name. Doing this would create negative value.
- dasil003 14y agoI'm not following your point. I'm saying that true delegation as defined by the article is in fact a useful tool for good software design. Maybe not as broadly useful as standard message forwarding, but something which deserves its own term.
- btilly 14y agoDelegation as defined by the article makes every method call made by the delegated to class part of the programming interface that you need to be aware of when choosing to delegate. Delegation as defined by GoF makes only a specified set of callbacks be part of that interface. That says that delegation as defined by GoF does more to promote modularity than the original definition, and therefore is more often going to be preferred in good software design over that defined by the article. This is not to say that there aren't cases where what the article promotes is not convenient. Violating modularity is usually convenient. But that is a convenience that we should always be wary of.
- peeters 14y agoDelegation is such a commonly-used English word that you don't get to have a monopoly on its definition. If I have two classes and one delegates to an instance of the other, then it's delegation. Just because Lieberman tried to give it a more refined definition in the context of OOP doesn't mean that the less refined use is incorrect. You don't get to take away my English words.
- saturnflyer 14y agoLieberman invented this term. It did not exist prior to his work. I have confirmed this with Lieberman himself as well as Jim Coplien and David Ungar. The Design Patterns book sought to clarify our language yet it has this error. I'm seeking to clarify our language.
- peeters 14y agoHe did not invent the term. "Delegate" and "delegation" have been around a lot longer than computers. Here's a definition: Delegate. Verb: Entrust (a task or responsibility) to another person, typically one who is less senior than oneself: "he delegates routine tasks". It's not hard to see how that would be analogous to a variety of situations in computing. If you want a term to be more pure, think of something more creative. Edit: That's not to take away from your point that the GoF actually cited Lieberman in their use of delegation. If they misunderstood his intention, sure raise that point.
- saturnflyer 14y agoIn programming terms, he did. I appreciate that it is an English language word and was initially what I thought it meant. But when he applied the term he meant it specifically. Otherwise, we already have a term for this: forwarding. So why not argue about people using "delegation" when they just mean "forwarding"?
- peeters 14y agoAlright, let's take it for a spin. What do you call the thing that you're forwarding to? The endpoint? The "nextLinkInChain"? Delegate seems pretty natural to me in most domains, but as you say, I've been poisoned by GoF.
- jcmoscon 14y agoMaybe the need of a Design Pattern means that the language is not powerful enough. PaulGraham said "Peter Norvig found that 16 of the 23 patterns in Design Patterns were 'invisible or simpler' in Lisp." http://www.norvig.com/design-patterns/ http://www.norvig.com/design-patterns/
- jcmoscon 14y agoDiscussion about this here: http://c2.com/cgi/wiki?AreDesignPatternsMissingLanguageFeatures http://c2.com/cgi/wiki?AreDesignPatternsMissingLanguageFeatu...
- btilly 14y agoThe td;lr of this post: this article is misguided according to usage, the history of the word "delegation", and the principles of good software design. One of the points of design patterns is to define a common language. The benefit of this is that it helps people understand one another. The fact that delegation as discussed in GoF is what everyone understands delegation to be is good enough reason to continue using the word "delegation" that way and to force him to find a new word for what he wants to say. Even if his definition was first. But his definition was NOT first. Sure, someone may have first used the term in OO programming in his sense of the word. But the word "delegation" has long-standing usage in the English language. It means, "Doing this is now your responsibility." In English there is no automatic implication that the person to whom things are delegated necessarily has access to the person who did the delegating. In practice, of course, there is. Which is why the software analogs include that. But in the real world it is clear when you intend to refer a question back to the original person, and when you do not. Therefore the long established and universally understood definition does NOT indicate that the person to whom you delegate has the option of choosing to intercept any and all questions you ask. So which behavior is preferable?. If I delegate to you, and then need to be aware of all of the methods that you define, all of your methods, both public and private, become part of the surface of the API between us. However the whole point of modularity is to have limited APIs between you and your components. Enlarging the API may be easier and more convenient, but it entwines code into spaghetti and is bad for your code base. So good software design says that of the two possible definitions of "delegation" we are comparing, we should prefer the one that makes it clear in the delegated to method when exactly it intends to go back to the delegated object versus when it is trying to send messages to itself. And the version that does that is the version that the Gang of Four used. Therefore he is wrong to say that delegation should be redefined to mean what he means. He is wrong to say that his definition is better grounded in the history of the word "delegation". And he's dead wrong that implementing his version of the word "delegation" is better software design than the current definition.
- saturnflyer 14y agoI never said delegation should be redefined. In fact I'm pointing out that the GoF did the redefining. In the history of Object-oriented programming "delegation" means what it was described to be. I never said that any particular implementation is "better software design". Please show me where you got these things that I supposedly said.
- peeters 14y agoTerminology arguments aside, I remember at least one occassion where I really wanted this in a GoF pattern. I had an interface Repo, with methods getA() and getB(). I wanted to overlay a transparent cache a la Proxy (http://en.wikipedia.org/wiki/Proxy_pattern http://en.wikipedia.org/wiki/Proxy_pattern, note its use of "delegate" in its description). So I had implementations CachingRepo and DataStoreRepo, the first would cache recent calls and the latter would make real calls. CachingRepo would have an instance of Repo that it delegates to on a cache miss. The issue was that DataStoreRepo.getA() relied on getB(). In a non-Lieberman delegation strategy, that B would always come from the data store, not my cache. If I understand correctly, in Lieberman delegation getB() could return the cached values, because its "self" would point to the CachingRepo, not "this" in a Java sense. It's not impossible to do this in Java, there's just not language support for it. The wiring would be cumbersome. Thanks for introducing me to Lieberman's work, but I'll stick with the de facto standard usage of "delegation".
- mlvljr 14y agoGod bless that OO dreamers! Always witty, and always far away from their evading (and silver :)) target...
- munificent 14y agoFrom Design Patterns (first edition): > Delegation is a way of making composition as powerful for reuse as inheritance [Lie86,JZ91]. In delegation, two objects are involved in handling a request: a receiving object delegates operations to its delegate. This is analogous to subclasses deferring requests to superclasses. But with inheritance, an inherited operation can always refer to the receiving object through the "this" member variable in C++ and "self" in Smalltalk. To achieve the same effect without delegation, the receiver passes itself to the delegate to let the delegated operation refer to the receiver. Sounds like they're perfectly clear and correct to me. As the author of the post points out the GoF don't actually show examples of delegation in the book and I don't recall them using the term much, so I don't see how they're perpetrating any misinformation here. > In JS we can assign a prototype: the equvalent of the parent slot in Self. No, .prototype is not equivalent to a parent slot in Self. It's closer to a traits object, I think. The unstandardized __proto__ property is equivalent to a parent slot in JS. > Yeah, Design Patterns showed examples in Java. And Java can’t do delegation. So is that a valid argument for rewriting the meaning of a term? Design Patterns is older than Java. Maybe later editions use it, but the original version used C++ and Smalltalk. Otherwise, good troll post, original author. I'm sure you'll get lots of traffic and people noticing your book. Well played!
- saturnflyer 14y agoThanks for clarifying. I had most of it written before posting and had forgotten the code samples. My copy of Design Patterns is packed up for a move. I've update it to refer to C++. Actually, people have visited, but few have stayed to read. My goal is to clarify the concept. I did plenty of research before writing this including asking Lieberman and others about it. I first wondered how everyone's notion could be wrong and doubted that my understanding was correct. This is a term that others have attempted to clarify as well http://javalab.cs.uni-bonn.de/research/darwin/delegation.html http://javalab.cs.uni-bonn.de/research/darwin/delegation.htm...
- scott_s 14y agoIf you agree with munificent, then perhaps you could soften your title and introduction to say that many people confuse what the GoF meant, not that the GoF are wrong.
- Jare 14y agoMany people agree on the words proposed by GoF, but not on the details of the meaning, and this is a frequent source of misunderstandings and useless debates. Over the years I have gone from fan of the book to considering it a net negative force in software engineering, a failed attempt that many people still believe in. (The other failure of the book is in educating people to blindly believe that applying a given pattern is always a good solution because, hey, it's a pattern) If you look at the details of the patterns as examples rather than definitions, and treat on the book as a general description of common situations, problems and approaches, then all is well.
- saraid216 14y agoIn my experience, GoF is most useful in that it says, "Patterns exist in software architecture as much as they do in physical architecture." The rest is details.
- alexyoung 14y agoIn my experience most implementations either have a way of binding the context per method (JavaScript), or use a loose convention of passing the sender as the first argument (Objective-C). It seems like the Ruby libraries cited are the real issue, rather than a fundamental misconception of the concept of delegates or indeed inversion of control as a whole.
- daemin 14y agoCorrect me if I am wrong, but it seems to me that (Lieberman) delegation is quite a dangerous concept when applied to the most popular object oriented languages. You're effectively calling another object's methods and masquerading yourself as that object, or to put it another way you're exposing all of your privates and implementation details to another object. Hence it is much more dangerous, and potentially quite incorrect, than just forwarding. The only safe way I can see this being done is by adding a reference to object A when calling/forwarding a method on object B. But that's just forwarding with extra data. Maybe I haven't worked enough with fully dynamic languages, but I don't really see much or any benefit to doing 'Lieberman' delegation, over and above other options.
- raganwald 14y agoLiberman deleation is fine-grained multiple inheritence. If I say I'm delegating the implementation of method foo to object bar, it sounds unsafe. If I say I'm inheriting the implementation of method foo from object bar, it seems safer, albeit not "classical OO."
- daemin 14y agoThanks, that makes far more sense to me.
- ehosca 14y agoi don't know about you but i'm getting sick and tired of these "marketing" posts with sensational titles. if you have a book to sell just say so, so we can directly skip your post.
- usr 14y agoI'm getting sick of them as well. Most of them follow the same formula by having a declarative statement pointing out that someone is either wrong or doesn't understand something or this that or the other will never work. They seem to be pretty popular on here though as many of them have lots of comments.
- Dylan16807 14y agoI ignored the book and learned about two different types of delegation today. I'm happy.