On Monday, July 23, 2001, at 09:08 pm, Tom Malone wrote: > Someone please tell me if this is an inappropriate question for this > list - > I don't want to irritate or offend anyone here. > What is the benefit of a true object-oriented language (Ruby), in which > everything is an object, as opposed to, say (arbitrarily) a language > that is > not strictly object-oriented (yet is still popular) like Java? > > Forgive the newbie his ignorance =) > > Tom > Okay, I'll have a bash. Sorry if this is a bit meandering. First, what is a 'true' OO language? There is a story (which I quote from memory, may not have all the details right) about a talk that Niklaus Wirth gave at Apple Computer about Oberon. He was some way into the talk when a chap at the back stood up and said, "So you say that Oberon doesn't have inheritance?" Wirth, "No, that's right" "And it doesn't have..." (insert here various things that Ruby and Smalltalk have, but Oberon doesn't). Wirth agreed. "Then how can you say that it is an Object-Oriented Language?" To which Wirth replies, "Well, who can say what is, and what isn't, an OO language?" Chap says, "I can, I'm Alan Kay, and I invented the term" According to Alan Kay, OO languages are defined by four things: Encapsulation, Information Hiding, Inheritance, and Polymorphism. As someone else pointed out, however, you can use a language that doesn't provide these things and still do OO programming by, essentially, providing them yourself; it is just difficult. On the other hand, Java shows that you can have a language that provides all of them, and throw the advantages away (Encapsulation - what about all those static methods for Maths, instead of encapsulating them with Integer etc, what about Graphics? Information Hiding - common practice of directly accessing instance variables, even in standard library. Polymorphism - strong typing gets in the way, as it takes too narrow a view of 'type'. Inheritance - you can't allow subclasses to access its inherited methods and variables without giving every other (unrelated) class in the package the same privilege). Back to your question, who cares if it isn't 'pure' OO? First, as someone else mentioned, consistency. I don't have to ask myself whether this is an object I can send messages to or a primitive type I pass to functions; I don't have to decide between two different collection types according to the sort of data I have. This means fewer errors. An interesting study looked at the number of Source Lines Of Code (SLOC) per function point required by different languages. As I recall, COBOL was 104, C++ and Java both 53, VB was 28, Smalltalk and Perl both 21. Then they looked at the number of errors in production code produced by programmers experienced in that language. I don't know all the figures, but I remember C++ was about 93, Java 50. This would be in large part because Java was simpler (no multiple inheritance, no templates, etc), and a great deal because of GC. Both are strongly typed, whereas Perl and Smalltalk are not (or rather, Smalltalk is very strongly typed, but it is the object that has type, not the variable reference), so, according to strong typing advocates, they should have more errors per line of code, although there are fewer lines of code to contain errors. In fact, the error rate for Smalltalk was 14 per function point. I haven't seen figures for Ruby, but I would bet it is down there in the low teens as well. Therefore, in a 'pure' OO language, I regard strong typing as a failed experiment. These are errors that should be caught by your unit tests (RUnit, which catch far more errors too). For me, OO is taking to a logical conclusion something that was gaining acceptance for some time before - the value of loosely-coupled code. It combined this with high-cohesion, which makes learning what the system can do easier. Loose coupling has high value in a software system, and OO is perhaps the best way to achieve it. Loose coupling means that maintenance, additional functionality, and refactoring are made easier, and much less error-prone. Hybrid OO languages tend to compromise on loose coupling, viz Java's tendency to expose object structures by allowing direct access to instance variables (and hence the Date mess). With primitive types, you need strong typing for type safety, but this makes refactoring difficult. Code reuse (either by aggregation or inheritance) is certainly important, but not as much as the hype made out. Polymorphism is of great value, and makes use of loose-coupling, to allow you to 'slot in' new classes in subsequent versions of a program without breaking a lot of code (case statements would break, for example). This is a more subtle form of code reuse, but important even so. Alun ap Rhisiart