Relay-Version: version B 2.10 5/3/83; site utzoo.UUCP Path: utzoo!mnetor!seismo!rutgers!mtune!mtx5c!mtx5d!mtx5a!mat From: mat@mtx5a.UUCP (m.terribile) Newsgroups: comp.lang.c++ Subject: Re: Re: Questions about C++ Message-ID: <1812@mtx5a.UUCP> Date: Sun, 14-Jun-87 03:13:37 EDT Article-I.D.: mtx5a.1812 Posted: Sun Jun 14 03:13:37 1987 Date-Received: Sun, 21-Jun-87 02:46:40 EDT References: <452@ivax.doc.ic.ac.uk> <125@otc.OZ> Distribution: comp Organization: AT&T Information Systems, Middletown, NJ 07748-4801. Lines: 104 This is one more voice in a large discussion. > > However, SIMULA allows an important 'other' style of initialization : > > > >> v = new car; > > > > which initialises v, but not to a vehicle-instance: to a car-instance [ car > > must be a subclass of vehicle ] > > > > C++ objects [vehemently] to this kind of use : probably because it has many > > implications for run-time behaviour. > > No. C++ is excellent for doing this sort of thing, but requires a bit of > practice. E.g: As noted, the use of an object of class *derived* in place of an object of type *base* is allowed (so long as the base class is public) and is one of C++'s main OOP features. And yes, there *are* many implications for runtime behaviour and they are all good. Because of the static typing structure (more on this later) there are no runtime checks necessary and the runtime costs are quite well contained. See the last couple paragraphs of 7.2.8 in The Book (first edition.) > > o Associated operators like 'in' and 'qua' [ see below ] aren't available > > ... > > > Explanation of 'in' and 'qua' : > > ----------------------------- > > > > 1). The boolean SIMULA function : > > > > i in c > > > > returns true if the instance, i, is an instance of the given class, c, > > or if i is an instance of any subclass of c [ false otherwise ] In C++, this information is known at compile time. If the object represented by *i* is not of a type derived from type *c*, you simply cannot use it as such. Excplicit type coercion (casting) overrides this limitation. This also protects you from attempting to use a method that will be unavailable at runtime -- a very desirable property for real-world software. > > whereas this is ok: > > > >> print (v qua car).wheels; > > If we had: > class Car : Vehicle { > public: > int wheels() { return 4; } > int refuel(); > }; > > then the following could be done: > > Vehicle *v = (Vehicle*) new Car; > > ((Car*)v)->refuel(); > > Note that explicit casting is necessary to initialise v, since here Car does > not have Vehicle as a public base class. Similarly, to access Car::fuel, a > further explicit cast is required. Needless to say, such constructions are > an indication of poor structure, and should be avoided as much as possible. Indeed. If we expect to ask how many wheels a vehicle has, the number of wheels ought to be a property of vehicles. > C++ does not use any features that require storing information of what types > a thing is derived from. This is for reasons of efficiency, and to adhere to > the basic philosophy that if something doesn't use a feature, it should not > have to pay for it. And the static-type structure has advantages for non-academic software, as noted above. > This is not to say the C++ is the final answer. For example, adding features > such as multiple inheritance, parametrized classes, exception handling, etc, > would be good. However, C++ is designed for high efficiency and these > features take time to develop under such circumstances. I find it interesting > how so much has already been added to C, which is considered quite a stable > language, without introducing serious backward incompatibility. The ongoing > enhancement of C++ seems to prove that it IS possible for a language to be > both reliable and stable, but also evolving. I've had the pleasure of meeting and chatting with Bjarne Stroustrup, and reading a number of papers that he has written. It seems clear to me from these that we are, in many ways, pushing the standard compile-link-debug environment very near its limits. As you say, the evolution of C++ must be slow if it is to be good. At present, the limits on that evolution seem to be 1) our ability to judge what is The Right Way To Do Something, and what is a merely a booby-trapped shortcut, 2) our current programming environments, and 3) the ability of one individual, no matter how gifted, to get X, Y, and Z done and working in a given amount of time. Would anyone care to examine #2 in a careful, stepwise way? -- from Mole End Mark Terribile (scrape .. dig ) mtx5b!mat (Please mail to mtx5b!mat, NOT mtx5a! mat, or to mtx5a!mtx5b!mat) (mtx5b!mole-end!mat will also reach me) ,.. .,, ,,, ..,***_*.