From: jimka on
Can someone explain the motiviation for the behavior of READ in the
following situations.

1. If the package "P" does not exist then P::name triggers an error.
It seems another quite reasonable behavior might be that READ should
simply create the package.

2. If the package "P" exists but does not contain "NAME", then P::name
interns "NAME" into P. It seems another resonable behavior might be to
allow the caller to determine whether or not to automatically intern
new symbols.

3. If the packagte "P" exists and contains "NAME", but "NAME" is not
interned or not exported, the reader signals an error when
cncountering P:NAME. Another reasonable behavior might be to allow
the caller to opt for automatically interning and exporting the
symbol.

4. All keywords go into the same package. "KEYWORD". What causes the
evaluator to evaluate keywords to themselves? Is it that they exist
in this package? The CL syntax for keywords is that the a : preceed
the name. Other than this extremly handy syntax, is there any other
reason one might want all keywords in the same package? Is there an
reasonable argument to allow keywords in other packages? Restated,
suppose a lisp did not support the : synax for keywords but insisted
that keywords by identifyable by their inital character being "?".
Would their be an advantage for that lisp to force all such keywords
into the same package?

-jim
From: RG on
In article
<93409517-5c5c-48e5-b9c6-9e2a2a064981(a)y30g2000yqh.googlegroups.com>,
jimka <jimka(a)rdrop.com> wrote:

> Can someone explain the motiviation for the behavior of READ in the
> following situations.
>
> 1. If the package "P" does not exist then P::name triggers an error.
> It seems another quite reasonable behavior might be that READ should
> simply create the package.

Not really. Packages are generally not created haphazardly. If P
doesn't exist, chances are good that P::name is a typo.

> 2. If the package "P" exists but does not contain "NAME", then P::name
> interns "NAME" into P. It seems another resonable behavior might be to
> allow the caller to determine whether or not to automatically intern
> new symbols.

Since the caller is almost always the REPL, how would that help?

BTW, you can actually get this behavior by grabbing a copy of:

http://darcs.informatimago.com/darcs/public/lisp/common-lisp/reader.lisp

and tweaking it to suit your tastes.

> 3. If the packagte "P" exists and contains "NAME", but "NAME" is not
> interned or not exported, the reader signals an error when
> cncountering P:NAME. Another reasonable behavior might be to allow
> the caller to opt for automatically interning and exporting the
> symbol.

No, because that could result in symbol conflicts for packages that use
P.

> 4. All keywords go into the same package. "KEYWORD". What causes the
> evaluator to evaluate keywords to themselves?

Section 2.3.5 of the standard.

> Is it that they exist in this package?

No. It's just a random hack: "It [the reader] also sets the
symbol-value of the newly-created symbol to that same symbol so that the
symbol will self-evaluate."

It is universal practice in CL implementations to not only set the
symbol-value of keywords to themselves, but also to define them as
constants. One could reasonably argue that that this is not conforming
behavior, but one would be wasting one's time.

> The CL syntax for keywords is that the a : preceed
> the name. Other than this extremly handy syntax, is there any other
> reason one might want all keywords in the same package?

Yes, to preserve print-read consistency.

> Is there an
> reasonable argument to allow keywords in other packages?

No. What would that even mean?

> Restated,
> suppose a lisp did not support the : synax for keywords but insisted
> that keywords by identifyable by their inital character being "?".
> Would their be an advantage for that lisp to force all such keywords
> into the same package?

That's incoherent. You've changed the meaning of the word "keyword"
without clearly defining how these neo-keywords would behave. But
whatever your intention here, you can almost certainly implement it
yourself by defining a reader macro on #\?.

rg
From: Tamas K Papp on
On Sun, 25 Apr 2010 07:06:48 -0700, jimka wrote:

> Can someone explain the motiviation for the behavior of READ in the
> following situations.
>
> 1. If the package "P" does not exist then P::name triggers an error. It
> seems another quite reasonable behavior might be that READ should simply
> create the package.

So each typo would create a new package, instead of an error message?
Please count me out.

> 2. If the package "P" exists but does not contain "NAME", then P::name
> interns "NAME" into P. It seems another resonable behavior might be to
> allow the caller to determine whether or not to automatically intern new
> symbols.

When you are reading a file, you are encountering new symbols. So

(defun foo (a b)
(expt (+ a b) 2))

would prompt me 3 times (provided I am using the CL package). So if I
am developing lisp, I would be constantly answering prompts. If I wanted
to waste my time answering prompts, I would just use Windows Vista.

> 3. If the packagte "P" exists and contains "NAME", but "NAME" is not
> interned or not exported, the reader signals an error when cncountering
> P:NAME. Another reasonable behavior might be to allow the caller to opt
> for automatically interning and exporting the symbol.

When symbols are not exported, that is usually for a good reason.

> 4. All keywords go into the same package. "KEYWORD". What causes the
> evaluator to evaluate keywords to themselves? Is it that they exist in
> this package? The CL syntax for keywords is that the a : preceed the

Keywords evaluate to themselves by definition. I don't understand the
"what causes" question, the standard says that they are, and the
implementation just makes sure that they do evaluate to themselves.

> name. Other than this extremly handy syntax, is there any other reason
> one might want all keywords in the same package? Is there an reasonable
> argument to allow keywords in other packages? Restated, suppose a lisp

Keywords are _defined_ to be in the keyword package. If the symbol is
in another package, it is no longer a keyword.

> did not support the : synax for keywords but insisted that keywords by
> identifyable by their inital character being "?". Would their be an
> advantage for that lisp to force all such keywords into the same
> package?

What is is that you want to achieve? If you just want symbols that
evaluate to themselves, you can make them do that:

(defconstant ?foo '?foo)

But I don't see an immediate use case.

Best,

Tamas
From: jimka on

> 4. All keywords go into the same package. "KEYWORD". What causes the
> evaluator to evaluate keywords to themselves? Is it that they exist
> in this package? The CL syntax for keywords is that the a : preceed
> the name. Other than this extremly handy syntax, is there any other
> reason one might want all keywords in the same package? Is there an
> reasonable argument to allow keywords in other packages? Restated,
> suppose a lisp did not support the : synax for keywords but insisted
> that keywords by identifyable by their inital character being "?".
> Would their be an advantage for that lisp to force all such keywords
> into the same package?
>
> -jim

It's obvious from the responses to this question that the question is
not stated very well. :-( Let me retry.

Common lisp, keywords happen to have three very useful properties.
1. they always evaluate to themselves
2. they always parse to the same symbol, regardless of the value of
*current-package*
3. key all have (are in) the same package: "KEYWORD"

These three properties are really orthogonal, but is it nice the CL
makes
sure they are all true simultaneously

If the only lisp you have ever used is common lisp or something very
common
lisp-like, you might understandably have trouble seperating the two
concepts
as you have not so many example of symbols which exhibit one behavior
without
exhibiting the other. (T is an example of a symbol which exhibits #1
and #2,
but not #3)

#1 means you cannot do the following
(setq :key 42)
will fail, but (eq :key ':key) returns t.

#2 means that even if the following functions are defined in different
packages, ...

;; in package A
(defun fun1 (x)
(eq x ':key))

;; in package B
(defun fun2 (x)
(eq x ':key))

....the the two functions behave the exact behavior, as opposed to the
following two functions which exhibit different behavior.

;; in package A
(defun fun3 (x)
(eq x 'key))

;; in package B
(defun fun4 (x)
(eq x 'key))

Now because CL combines #1 and #2, you can write fun1 and fun2 without
quoting the keyword.

Now, what was my question?

It was basically this: if a lisp allows users to create symbols which
have attribute #1
or #2 independently, does this eliminate the need for a single package
which contains them all?

So I don't understand whether CL conflates the 3 attributes into one
because it only makes
sense to do so, or whether the choice is an arbitrary one.

-jim
From: Pascal J. Bourguignon on
jimka <jimka(a)rdrop.com> writes:

> 4. All keywords go into the same package. "KEYWORD". What causes the
> evaluator to evaluate keywords to themselves? Is it that they exist
> in this package? The CL syntax for keywords is that the a : preceed
> the name. Other than this extremly handy syntax, is there any other
> reason one might want all keywords in the same package?

(eq ':x ':x) --> true is a good reason.

> Is there an reasonable argument to allow keywords in other packages? Restated,
> suppose a lisp did not support the : synax for keywords but insisted
> that keywords by identifyable by their inital character being "?".
> Would their be an advantage for that lisp to force all such keywords
> into the same package?

If they wouldn't have to go to a single package, to what package should
they go?

Notably, are they interned in a package at read-time or at run-time?

Interning them at run-time would not be possible to implement as a
reader macro if you want them to be interned even when quoted:

(quote (?a ?b)) --> ???

(loop for *package* in (list (find-package "A")
(find-package "B")
(find-package "C"))
collect '(?x))

could not give a list of three different symbols, without breaking the
semantics of QUOTE.


So we have to intern them at read-time. CL:*PACKAGE* is the logical
package where we could intern them.

(set-macro-character #\?
(lambda (s c)
(declare (ignore c))
(let ((sym (intern (concatenate 'string "?" (string (read s))))))
(eval `(defconstant ,sym ',sym))
sym))
t)

Notice that we have to use (eval `(defconstant ...)), because there's no
standard API to make a constant at "run-time", this is implementation
dependant. And we want them to be constant, don't we? Otherwise we
could just use:
(progn (declaim (special ,sym)) (setf (symbol-value ',sym) ',sym)).

(read-from-string "(?a ?b ?c)") --> (?A ?B ?C) ;
10

(setf *print-readably* t)
--> T

(loop :for n :in '("A" "B" "C")
:for k :in '("?X" "?Y" "?Z")
:collect (let ((*package* (make-package n :use nil))) (read-from-string k)))
--> (|A|::|?X| |B|::|?Y| |C|::|?Z|)

(loop :for n :in '("A" "B" "C")
:for k :in '("?X" "?X" "?X")
:collect (let ((*package* (find-package n))) (read-from-string k)))
--> (|A|::|?X| |B|::|?X| |C|::|?X|)


Now, the question is what did you earn by making "keywords" in different
packages? Now you have to qualify them with a package to get the one
you want!



In conclusion, asking keywords to be interned in different packages is
like asking why spheres don't have corners, and what would I get if I
made a sphere with corners.

--
__Pascal Bourguignon__