[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: intern



	
    From: hpfclp!diamant@hplabs.ARPA
    Subject: Re: intern
    
	 From: hplabs!NGALL@G.BBN.COM
	 Subject: Re: intern
	 
	    
	 What I would like to see is the following:
	 
	 1. Leave the stipulation on page 172 that INTERN fix-up the package
	 slot of an interned symbol.
	 
    It may be better to remove the definition of the verb "intern" on pg. 172
    since the verb is not used elsewhere in the chapter.  See my comments below.
But the verb is used by Common Lispers, and many times incorrectly (e.g., the
current definition of the verb is incorrectly applied to symbols
instead of names).  So I would like to see the use of INTERN as a verb
and adjective defined about where it is now.

	 2. Refer to pg. 172 in the def. of INTERN.
    I think it would be a better idea to completely define the functionality of
    INTERN in one place (preferably on page 184).
Agreed.
    
	 3. Make IMPORT also fix up the package slot.
    I agree.
	 
	 4. In UNITERN, after warning about homeless interned symbols, cf.
	 IMPORT for fixing things up.
	 
	 5. Make clear that FIND-SYMBOL has NO SIDE EFFECTS.  And point out
	 that it is the only way of mapping a name to a homeless interned
	 symbol.
	 
    For the reasons described below, I would suggest stating that INTERN also
    does not modify already-existing symbols.
Agreed.
    
    This appears O.K. at first, but consider the following example:
	 
    (in-package "FOO")
    (intern "X")
    (export 'x)
    (in-package "BAR" :use '("FOO"))
    (export 'foo:x)
    (unintern 'foo:x (find-package "FOO"))
    (in-package "BAZ" :use '("BAR"))
    (intern "X")
    
    If we follow the proposed definition of intern, x is now internally available
    in BAR, available by inheritance in BAZ, but its package cell is BAZ. Now,
    if we (unintern 'bar:x (find-package "BAR")), then the symbol will
    disappear even though its home package was not BAR.  Alternately, if we
    (unuse-package "BAR" (find-package "BAZ")), then bar:x has a home package of
    BAZ, but is not available in BAZ. This seems to violate print-read consinstency.
    
    (in-package "FOOBAR")
    (eq
      (read-from-string (with-output-to-string (*standard-output*) (print 'bar:x)))
      'bar:x))
    This will return nil, instead of t.
    
    An alternative is to have intern not set the home package, but be functionally
    equivalent to:
    
    (defun intern (name &optional (package *package*))
      (or (find-symbol name package)
	  (import (make-symbol name) package))))
    
    This has the unfortunate property of having intern return uninterned symbols
    in some cases.  See the above example.
And of always importing NIL :-).
    
    It seems that we are back to the original statement you made that IMPORT is
    the only function permitted to change the package cell (however, the reasons
    are more complicated than first suspected).  Would anyone care to comment on
    this?  
Since UNINTERN is the only other function that is allowed to modify
the package cell, perhaps CLtL should state either that:

1.  It is an error to UNINTERN a symbol from its home package if it is
present in some other package; or,

2.  An error is signaled in case 1 [I prefer this case.]

Saying (1) would at least warn people that "all bets are off" if they
create an accessible but unowned symbol and would allow
implementations that were concerned about it to signal an error.
Requiring (2) would be a bit more overhead, but since UNINTERN is
rarely used (right?), I think it would be acceptable.

    By the way, it may be a good idea to make the shadowing-import explicitly
    state the same clarification.
Agreed.