toad@nl.cs.cmu.edu (Todd Kaufmann) (10/25/89)
Just an informal survey... What do different lisps offer as alternative control structures or augmentation? I'm talking of features like encapsulate, advise, hooks, OO/methods, and maybe other things I don't know about. What do you find useful (and actually use), in what functionality (with respect to what is offered)? Where below are my ideas flawed, or off in details?: I think encapsulate and advise (or advice?) are the same thing: they let you modify an existing definition, giving you access to (some of) the arguments, previous body of definition, and return value. advise can go :before, :after, or :around (not too sure about the latter). Disadvantages: too much freedom (?) (ie, you can do it anywhere, but when you're trying to patch into a big system to get your stuff to work with it, how are you sure "where" is the right place?). May be implementation dependent (ie, access to function/args/environment). I'm not sure this is true. In a later message I may post an attempt at such a function, but I'm not sure now how much I'm assuming from familiarity with the systems I know. History Q: encapsulate is from symbolics (or does it go back to maclisp?); advise is from interlisp (xerox). Hooks are best for augmenting an interface.. they give a programmer an "in". Usually they are decided in advance by the author of the program. Disadvantage: the author must have enough foresight to put in all the hooks in all the right places. For example, I'm redesigning a large system (a KB ms/editor/browser), and trying to make all the modules separable and fully functional alone, but planning in advance ways they can interact. Say, for example, one module does various checking, and produces warnings when things aren't defined. When the dialog module is installed, it can be called to query/help/guide the user in a more friendly way. (*1) History Q: who invented the "hook"? I'm more interested in the road it took to present day lisps (or more likely, their editors like zemacs, gnu, hemlock), than byte-level patches. Did TECO have hooks? I think so.. Does your lisp have EVALHOOK? Another method is object-oriented systems, and defining your own/new (sub-)class. Then, to get the "normal" behavior, you call the parent method as applicable. Disadvantage: most OO systems (a) have too much baggage for what they give, (in my experience)--they take more space and time, including (b) the initial time to learn. They are okay for development, but if you know what and how you're doing, it's generally not necessary, or the places where you need "methods" (c) are really very few, and can be fixed by simpler means, like typecase or datadriven methods. (a) and (c) are very similar. (b) is an investment that needs to be weighed. I'd like to see a simple hierarchical dispatch method that can classifier by type/predicate.. (what when multiple matches occur? How does CLOS handle appropriate method choice? How can you specify multiply applicable methods?) On a slightly different topic: how about Scheme and other dialects, especially parallel/other architecture designs. I'm especially interested in "futures".. who has them, and when do you (need to) use them? [A pointer to the R^3 (^4?) report is welcome, especially from a CMU-ite] How translatable are these into serial (ie, standard common lisp) ? Example Use: multiple, concurrent dialog threads. You can't have each thread of dialog stopping lisp with (read). How do you avoid this, without making the dialog-writers contort themselves too much? I think I have a solution, which requires some separation of interaction control from program control by explicit specification, yet allows the writer to still write (read) or similar; this system just goes away at this point, and comes back later with the input (say, when the user has hit <enter> in the appropriate window; meanwhile other threads of dialog may have come and gone-- perhaps the current one is no longer applicable--we must check that too.) I think I've come up with a solution to this problem, or at least some good examples; if you're more interested, I can send you a copy of a paper I'm working on. Also, with the above (*1) example of using hooks for module-interfaces, it would also be nice to have a single-thread work alone, but also be able to throw it into an environment where there are others too. Why should programs have to be re-written for this? I'm not sure how understandable this problem is unless you've banged your head on it and tried to do such user interfaces in an elegant way. And if you think you have a good solution, I'd like to hear it. Okay, thanks for listening, throw out some ideas. -todd -- INTERNET: toad@cs.cmu.edu; BITNET: toad%nl.cs.cmu.edu@cmccvb.bitnet UUCP: ...!{uunet, ucbvax, harvard}!nl.cs.cmu.edu!toad FAX: 412/268-6298 attn:TK