blythe@kuhub.cc.ukans.edu (06/24/91)
In C++'s effort to encapsulate data and methods, it has missed some points. A Proposal: Overloading Keywords One of the best things about C++ is its ability to overload an operator for a certain combination of objects. These operators are then implemented as a function by the compiler. Why not keywords also? In specific, the selection keywords (if...else and switch) and the iteration keywords (while, do, and for) are the only keywords I see having good potential when overloaded. Take the following normal code as my example: class An_Object { int ready; ... public: int status(void); ... }; int An_Object::status(void) { return(ready); } int main(void) { An_Object object; ... while(object.status()) { ... } ... } The code deciding the termination of the loop is in the object, which is good encapsulation. I was once told that the best objects will know everything you plan to do with them, implemented through member functions (methods). Notice though that the while statement is directly interacting with the object; the object doesn't know how to execute a loop so the while is obviously needed. What I am saying is that the object should know how to interact with the while, which is even better encapsulation than the above example. Take the following code for example: class An_Object { int ready; ... public: An_Object keyword while; ... }; An_Object::keyword while { ready; //statement to be evaluated by a while loop } int main(void) { An_Object object; ... while(object) //better encapsulation { ... } ... } Every time the while loop is executed the statement defined inside the object is evaluated, it's that simple for the while. Overloading other keywords may prove to be a little more challenging, but not much. Overloaded operators are implemented as functions by C++ compilers. Overloaded keywords could be implemented as functions placed inside the real keywords or the statements could simply be placed in the correct place by a preprocessor. Overloaded operators let us get away from code like this: result = add(complex_number_1, complex_number_2); to simply: result = complex_number_1 + complex_number_2; Overloaded keywords could let us get away from code like this: while(object.status()) {...} to simply: while(object) {...} Thank you for your time. Any comments are welcome. Garrett Arch Blythe.
barmar@think.com (Barry Margolin) (06/24/91)
In article <1991Jun23.223737.31644@kuhub.cc.ukans.edu> blythe@kuhub.cc.ukans.edu writes: > One of the best things about C++ is its ability to overload an >operator for a certain combination of objects. These operators are then >implemented as a function by the compiler. Why not keywords also? In >specific, the selection keywords (if...else and switch) and the iteration >keywords (while, do, and for) are the only keywords I see having good >potential when overloaded. If C++ had a real boolean type, and required the test expression of an "if", "while", "do", and "for" statements to be of this type (perhaps with a built-in conversion from integral and pointer types, for back-compatibility) then much of this could be done by defining a conversion from the class to boolean. The "for" statement is a bit more complex if you want the overloading to be able to take over the initialization and stepping as well. You'd probably need an alternative syntax; maybe: for (<lval> = <expression>) <statement> where <expression> should evaluate to a class object. The interface would probably be similar to iterators in CLU. I'm not sure how you could combine traditional "for" loops with the overloaded kind in one statement. I'm not sure what an overloaded "switch" statement would be like. Would the labels still be integer constants? If so, then a conversion from the class to int would be sufficient. Of course, all these suggestions about using conversions only work if the same conversion is useful in all the contexts. If you want the test in a "while" statement to be true in a different case from the test in an "if" statement, it won't work. However, I think that would be a very bad idea. The equivalence between while (<expr>) <statement> and <label>: if (<expr>) { <statement> goto <label>; } is generally considered fundamental; choices between the various forms of control flow are supposed to be based on style, not semantics. -- Barry Margolin, Thinking Machines Corp. barmar@think.com {uunet,harvard}!think!barmar
alanb@sdl.mdcbbs.com (06/25/91)
In article <1991Jun24.163530.14631@Think.COM>, barmar@think.com (Barry Margolin) writes: > In article <1991Jun23.223737.31644@kuhub.cc.ukans.edu> blythe@kuhub.cc.ukans.edu writes: >> One of the best things about C++ is its ability to overload an >>operator for a certain combination of objects. These operators are then >>implemented as a function by the compiler. Why not keywords also? In >>specific, the selection keywords (if...else and switch) and the iteration >>keywords (while, do, and for) are the only keywords I see having good >>potential when overloaded. > > If C++ had a real boolean type, and required the test expression of an > "if", "while", "do", and "for" statements to be of this type (perhaps with > a built-in conversion from integral and pointer types, for > back-compatibility) then much of this could be done by defining a > conversion from the class to boolean. > [Discussion of "for" omitted. CLU style iterators would be nice though.] We have a C preprocessor that provides a boolean type and enforces the rule that test expressions must be booleans (e.g. if (pointer != NULL), not if (pointer)). (Now we use C++, we just have a coding convention). If you allow conversion from integral and pointer types, you have lost the type enforcement you might want, so why not just define operator (void *) for the classes you want to use in while loops? Something like { if (my_status) return this; else return NULL ); if (anobject) { foo(); } is now equivalent to if (anobject.status()) { foo(); } and while uses the same test as if. (this assumes you never want to coerce to a pointer other than when your if/while condition is true - in many cases this is reasonable.) (The preprocessor also provided function prototypes before ANSI C was around, and workarounds for assorted platform compiler bugs - I'm not claiming that just having a boolean type is necessarily worth the effort). > Barry Margolin, Thinking Machines Corp. > > barmar@think.com > {uunet,harvard}!think!barmar Alan Braggins alanb@sdl.mdcbbs.com "Any resemblance between these opinions,..."
rae@alias.com (Reid Ellis) (06/26/91)
<blythe@kuhub.cc.ukans.edu> writes: |while(object) //better encapsulation |{ | ... |} ... |Overloaded keywords could let us get away from code like this: | while(object.status()) {...} |to simply: | while(object) {...} This can easily be accomplished right now by providing an "operator void *" method, like the iostream classes do. This is why you can say: while(cin) { cin >> buf; // etc.. } Reid -- Reid Ellis rae@utcs.toronto.edu || rae@alias.com CDA0610@applelink.apple.com || +1 416 362 9181 [work]
marc@dumbcat.sf.ca.us (Marco S Hyman) (06/28/91)
In article <1991Jun25.224022.20072@alias.com> rae@alias.com (Reid Ellis) writes: > This can easily be accomplished right now by providing an "operator > void *" method, like the iostream classes do. This is why you can say: > > while(cin) > { > cin >> buf; > // etc.. > } Many have recommended overloading void * to do this instead of overloading int (which happens to be my favorite). Is there a particular reason for prefering void * to int? // marc -- // home: marc@dumbcat.sf.ca.us pacbell!dumbcat!marc // work: marc@ascend.com uunet!aria!marc