Path: utzoo!utgpu!news-server.csri.toronto.edu!cs.utexas.edu!sdd.hp.com!think.com!samsung!munnari.oz.au!goanna!ok From: ok@goanna.cs.rmit.oz.au (Richard A. O'Keefe) Newsgroups: comp.lang.scheme Subject: Making programs out of modules in Scheme Message-ID: <6384@goanna.cs.rmit.oz.au> Date: 19 Jun 91 07:11:20 GMT Organization: Comp Sci, RMIT, Melbourne, Australia Lines: 73 I just received E-mail from someone who believes that Scheme as it currently stands does not have the facilities required to build a library out of modules. I claim that he is wrong, that Scheme as it stands provides everything we need to build programs out of modules that do not interfere with each other's name space. All it takes to do this is to define ONE globally accessible function. I'm posting this in order to receive constructive criticism. Please note that of two distinct claims: (a) this is what a good module facility for Scheme would look like, and (b) this is a simple facility we can build with existing tools and it will (just) do the job, I am making claim (b), not claim (a). Here's the interface of the function. (library 'register ModuleName:symbol FileString:string) The idea is to keep (system-dependent) file names out of the library files themselves. A ``master'' file, which would be site dependent as well as OS dependent, maps module names to the file name to be given to load. This file must be loaded in some site-specific manner; after that everything is portable. (library 'define ModuleName:symbol ExportName:symbol Value:any) A module exports things by calling this. The value is somehow associated with (ModuleName,ExportName), replacing any previous association. (library 'require ModuleName:symbol) This is exactly like QP's ensure_loaded/1; if no such 'require command has ever been given before, it is recorded that the load has been started, and (load FileString) is done. In a system where you can specify the environment to load, one would load into user-initial-environment or its equivalent. (library 'value Modulename:symbol ExportName:symbol) This returns the value 'defined for (ModuleName,ExportName). It is an error to ask for a symbol which was not 'defined. If the Modulename has not been loaded, it does a 'require first. (Which doesn't _quite_ make 'require redundant.) Here's how it would be used. A library file would look like (let (-local variables-) (library 'require 'mod1) ; this uses mod1 (library 'require 'mod2) ; this uses mod2 (let ((foo (library 'value 'mod1 'foo)) (bar (library 'value 'mod2 'fred)) ...) ; other such imports (define ...) ; define local and (define ...) ; exported things ... ; in any mix (library 'define 'thismod 'ugh snark) (library 'define 'thismod 'zoo boojum) ... ; other exports 'thismod)) That's it. The entire file would be one let-expression. The implementation of (library mod . rest) is so trivial that it is left as an exercise for the reader. This suffices to show that the LANGUAGE permits the construction of modular libraries. Now, whether any particular Scheme _implementation_ handles such files well is another matter. -- Q: What should I know about quicksort? A: That it is *slow*. Q: When should I use it? A: When you have only 256 words of main storage.