noren@dinl.uucp (Charles Noren) (02/22/90)
I knows this must fall under frequently asked questions and probably should be posted under comp.lang.religion..., but We are about to move from the standard C compiler on a Sun 3 to either C++ or Objective C. I would like some recommendations on which language to use. I know C++ is much more popular than Objective C, but I would like some insights into the differences of the languages and their impact on software development. Thanks in advance. -- Chuck Noren NET: ncar!dinl!noren US-MAIL: Martin Marietta I&CS, MS XL8058, P.O. Box 1260, Denver, CO 80201-1260 Phone: (303) 971-7930
jsweet@slsaux.arc.nasa.gov (John Sweet) (03/02/90)
Though I walk in the Valley of Early-Binding and "Real-time" systems, the Lord is at my side. I shall lay down my debugger, and walk the paths of righeousness. Objective-C is my sheppard, and I do not want. Balenced Credentials: Six-years C, C++, Objective-C programming on Vax, Sun, Mac, DOS, Real-time boards. Written several compilers, "C" language extensions, yacc/lex type stuff. Two-years of 80-hour/week experience for a small "start-up" developing a 'real-world' commercial product in Objective-C (w/database&windows). Two-months of 80-hour/week work to create my own personal, C++ compiler. (At the time I wanted to really know C++, and I didn't know about GNU). Obviously, the deciding factor in you're decision should be your "application". This sounds terribly wishy-washy, but you will chose in your context for your context. Since there are infinite application contexts, we must find an abstraction for our basis of generalization. I propose we use "boundedness". If your application is "user-bounded", as opposed to interrupt-latency-bounded, then the time it takes for the user to move the mouse is very large relative to the time it takes for Objective-C to dispatch a message. This means that the time/keystrokes/clicking it takes for the user to complete a task, dominates the equation: Task Time = UserTime + ComputeTime + I/O_Time The last time I was a USER, the quantity on the left hand side of this equation was very important to me. Why choose Objective-C? - StepStone is an excellent company. - Next has chosen Objective-C. - IBM (I believe) has just announced a new Unix platform which comes standard with Objective-C. These reasons are political, and, in my opinion, balance the explicit (or implicit) endorsements by AT&T, Apple, and GNU. - Objective-C is an abstract superset of C++, (By this I mean that everything you can do in C++, i.e. static binding without the message dispatcher, except for inline functions - which is not really an abstraction - you can do in Objc, but they are not gramatically supersets). - Self-referential applications are more powererful. (Don't throw away your symbol table at compile-time in the name of efficiency and then torture yourself writing lines of code to regenerated it). - Professionally maintained, supported, and documented Class library. (Like Smalltalk the best OOPL's come complete with libraries of Inheritable Objects created by wise parental units). - Stepstone has ported its Class libraries to a large number of platforms, and assists companies in porting to new platforms. (This includes a cut of any royalties on the new machine). - You can buy and use off the shelf C-libraries from Doctor Dobbs, et al, just like C and C++. - The mesage dispatcher frees you from compile-time circular references and those really nasty C++ makefiles with all their dependencies to ensure that their compiler's contextually bloated symbol table is loaded with all those constants. - This make OOPs very difficult: #define OffsetOfFooMethod 16 (*(myPseudoObject->vfunc_table[OffsetOfFooMethod]))( arg0, arg1 ); /* I left out the casts and time-hashed function names */ (NOTE: if you looked up the offset of the foo method at run-time, and allowed different classes to (without expanding the consumer's context) implement foo at different offsets in their virtual function table (i.e. their virtual interface), then you would be going down the OOP road and feeling glad, glad, glad..) - This makes OOPs much easier: if ( [anyInstance respondsTo:"foo"] == YES ) [ anyInstance foo ]; It's kindof like when you're looking at that loop wondering why, no matter how you program it, one boundary condition or the other messes you up... And then you realize that, if you declare another variable and keep arround that essentail piece of information that, by throwing it away, was making your life so difficult... Sometimes that essential piece of information has a larger context than a for loop... C++ programmers wake up!!! By throwing away you symbol table at compile time you are making your life more difficult than it need be. Try Objective-C. Good luck, j.s.s. At times it is difficult to tell the saved from the damned when they are all talking in tongues.
bader+@andrew.cmu.edu (Miles Bader) (03/03/90)
Just for fun, here are my six favorite icky bits in Objective-C 4.0 on the next machine, circa January 1989: 1) It currently uses a single namespace for method templates, regardless of the type of the receiver. This results in warnings when two (totally independent) classes use the same method name but with different argument or return types. It *should* warn only if the type of the receiver is a superclass of the two classes with conflicting methods (such as when it's an id). This is VERY IRRITATING, as extremely common cases result in this (e.g. [Float create:1.0] & [Int create:1]). 2) It currently uses a single namespace for the instance variables of an object of a given type AND all its superclasses' instance variables. Instance variables should be known only to the implementation of a class; its subclasses shouldn't have to worry about name-clashes with their own instance variables (and conversely, shouldn't have such easy access to their superclasses instance variables). 3) It should not warn about implicit casts from a type to one of that type's superclasses. (e.g. Object *foo=[SubTypeOfObject new]; should elicit no warnings). The c-compiler seems to be doing the complaining, so objective-c should put real casts into the c-code it outputs. 4) There should be a pseudo-type that is always the same as the type of the receiver at compile time, so that methods inherited by a subclass that return (or have an argument of) that type don't have to be unnecessarily casted, in cases where it doesn't make sense to do so. Example: @interface A {} -(ReceiverType *)self; // stupid method just returns self @end @interface B : A {} // inherits the self method from A @end One can then do: {B *var1=[B new], *var2=[B self];} without warning messages. One can acheive this by using the (id) type, but at the expense of compile-time type-checking in these cases. Indeed, the +new class method in Object should probably return (ReceiverType *). 5) Apparently, a unique, global symbol is declared by the objc pre-processor in each file, with a name constructed from the filename. This prevents users from using filenames that are the same as any filename used in the objc library that ends up being linked! It doesn't actually give an error to this effect, you just get a multiply defined symbol error from the linker. Users definitely shouldn't have to worry about name-clashes with the filenames used in the objc library! 6) If you reference a class by using it as a type in it's own include file, objective-c uses the contents of the instance variable declaration block as the contents of TWO structures in the resulting include file. This breaks if any of the instance variables are non-anonymous structures (as it results in declaring those structures twice). As NeXT include files often contain such non-anonymous structures in their instance variables, this shows up frequently for me.