------ art_16051_31920436.1191764450226 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit Content-Disposition: inline On 10/6/07, MenTaLguY <mental / rydia.net> wrote: > > On Sun, 2007-10-07 at 08:38 +0900, MenTaLguY wrote: > ... Actually, I guess this applies to having methods in general. The > classic ellipse-versus-circle thing is a great example: "is-a" in the > model domain (shapes) is exactly the opposite from "is-a" in the class > domain, at least in terms of Liskov substitutability. It's really unfortunately that the whole "is-a" idea got introduced into OOP, because it's not sufficient to represent inheritance. The example of shapes is a good one and worth emphasizing: Square < Rectangle or Rectangle < Square ? For most people, real-world intuition leans toward the first one. However, try writing a unit test for Rectangle where you can vary the height and width independently, then substitute a Square. It doesn't work. The implication of the Liskov Substitution Principle (LSP) is that we really need to talk about "behaves as a" relationships, not structural "is a" relationships. There is one other interesting point about this. LSP is context dependent; it depends on the "client's" expectations for behavior. While Square < Rectangle fails for the test "client" that wants to vary the height and width, it probably works just fine for another client that just wants to use read-only methods like #draw() to render shapes. dean -- Dean Wampler http://www.objectmentor.com http://www.aspectprogramming.com http://aquarium.rubyforge.org http://www.contract4j.org ------ art_16051_31920436.1191764450226--