Common lisp about naming packages and using them - common-lisp

I try to use Common Lisp packages, but I have several (probably naming conventions) problems, first is the use of "#:" it seems not necessary but is like sharp-quote in functions that is better to use depending on your context.
(defpackage #:match-test
(:use #:match
#:fiveam
#:cl)
(:export #:run!
#:test-match)
(:documentation "Test package for testing match project 1 of CS202"))
Then is in how to use that package
(in-package #:match-test)
(in-package :match-test)
(in-package match-test)
it works, but when I want to delete that package it only works with:
CL-USER> (delete-package (in-package #:match-test))
#<BOOLEAN <<error printing object>> {2010004F}>
it gives that error, but it makes the job done. It seems working with the package as an object, I also do not understand the hyperspec, is a problem that I need to learn CLOS, that is true I'm a beginner learning Lisp, but I suppose that I can get a easy clarifying for my doubts.
I hope that I said it quite clearly.
Finally I want to say that I used emacs + sly + roswell and
CL-USER> (lisp-implementation-type)
"SBCL"
CL-USER> (lisp-implementation-version)
"1.4.6"

DEFPACKAGE and IN-PACKAGE are defined as macros. They take a literal name - a string designator: foobar, |FOOBAR|, #:FOOBAR, :FOOBAR or "FOOBAR".
DELETE-PACKAGE is a function and expects a string designator, too. But since it is a function, the argument is evaluated. This means: if you want to pass the name, you have to quote it - if it is a symbol not in the keyword package. Strings and keyword symbols are self-evaluating and don't need to be quoted. Valid arguments to DELETE-PACKAGE are for example:
'foobar
'|FOOBAR|
'#:FOOBAR
:FOOBAR or ':FOOBAR
"FOOBAR" or '"FOOBAR"
Since DELETE-PACKAGE is a function, the argument gets evaluated -> you can also evaluate variables, function calls, ... as argument.
The Error: Deleting the current package
LispWorks:
CL-USER 43 > (delete-package (in-package #:match-test))
Error: Cannot delete the current package, #<The MATCH-TEST package, 0/16 internal, 2/16 external>.
1 (abort) Return to top loop level 0.
SBCL:
* (delete-package (in-package #:match-test))
debugger invoked on a SIMPLE-TYPE-ERROR in thread
#<THREAD "main thread" RUNNING {10005605B3}>:
*PACKAGE* can't be a deleted package:
It has been reset to #<PACKAGE "COMMON-LISP-USER">.
Your code tries to delete the current package - you just used IN-PACKAGE to make it the current package - deleting the current package is usually not a good idea. You are shooting yourself in the foot. A Lisp might prevent that (like my example in LispWorks) or allow it - but then you have to live with the consequence.

Related

Why do we specifiy packages using pound colon in Common Lisp?

New Common Lisper here. I have seen packages being declared with the pound colon syntax, as in (defpackage #:foo), but I have also seen them defined as plain keywords, as (defpackage :foo).
Which is considered "better"? What is the difference between these two? I read somewhere that pound colon simply means the keyword isn't interned. Is that true? If so, what are the advantages to defining a package with an uninterned keyword?
Package names are strings, but you can designate them using symbols, so you have basically the following options:
1. (defpackage foo ...)
2. (defpackage "FOO" ...)
3. (defpackage :foo ...)
4. (defpackage #:foo ...)
It is true that #:foo is an uninterned symbol, and the reason some people prefer to use that syntax is precisely because it does not "pollute" the current package (1) or the keyword package (3). Usually (1) is a big No because your defpackage form has a side-effect on whatever package is current, which is bad. At least (3) is more deterministic, you always pollute the keyword package.
Note that "polluting" is not so much a problem of having too many symbols in a package, but also the fact that it is harder to reverse the operation: delete-package cleans the package designated by the symbol, but there is still a symbol interned in another package that probably was not there before defpackage (and if it already was there, you don't want to unintern it).
Some people don't mind and use keyword symbols everywhere, and it is not "bad", it just has a potential for being a source of problems in some corner cases. It is usually better to use either a string (2) or an uninterned symbol (4).
The advantage of strings over symbols (interned or not) is that you control the case: it is possible to have different packages with names that are only distinct in case (e.g. "test" vs "TEST"), and while the standard defines how symbols are read by default (upcased), you don't know in advance if your package definition will be read by a Lisp environment that is setup in a standard way or a custom way (e.g. inverting the case before interning).
So ideally it should be more robust to use always literal strings: they do not intern a symbol and the case is explicit.
However, for some reason people tend to prefer writing #:foo: probably because it is not written in uppercase, or because there is no need for quotes, etc. I am not sure why honestly (strings are often a code smell in other circumstances so maybe we tend to avoid them).
Anyway, it has become a bit customary to use uninterned symbols. This is usually not a problem because (i) people tend to use the standard readtable and (ii) in case they customize it, it is quite stable during the execution of a Lisp environment: whether you upcase or downcase the symbol in the defpackage of some package P, the symbol will be read the same way in the (:use P) clause of another defpackage.
Package names are strings. But it is a good idea to specify them as symbols, because this buys you immunity to variants of CL which which do not have the same case behaviour as CL. As an example, Allegro CL has (or used to have: I have not looked at it for at least a decade) a mode where everything was lower-case by default. In that mode (symbol-name 'foo) would be "foo", and all the standard CL symbols were lower-case versions of themselves (so (symbol-name 'symbol-name) was "symbol-name".
If you wanted to write code which had any chance of running in an environment like that, you couldn't give packages names which were strings:
(defpackage "FOO"
...)
would mean that, in future, you'd need to type FOO:x and so on, which was horrible. Even worse, if you said
(defpackage "FOO"
...
(:export "X"))
You'd now have to type FOO:X. And something like this:
(defpackage "FOO"
(:use "CL")
(:export "X"))
would fail dismally because there was no package whose name was "CL" at all: its name, of course, was "cl".
So if you needed things to work with that environment you really wanted to type package names – and symbol names in packages – as symbols.
This also would mean that your code would have a chance of running in some future CL variant which really was lower-case, which many people assumed would probably happen at some point, since case-sensitive lower-case-preferred languages had clearly won by the late 1980s.
Given that there's a question of where you want the names to be interned. For symbols in a package it is generally very undesirable to intern them in the current package:
(defpackage foo
(:export x y z))
(use-package 'foo)
will fail.
So then there are two obvious choices:
intern things in the keyword package;
don't intern them.
It does not make much difference which you do in practice. Personally I intern package names in the keyword package as I want completion to work on them, but do not intern symbol names, because that seems just to be gratuitous clutter. So my package definitions look like
(defpackage :foo
(:use :cl ...)
(:export #:x #:y ...))

Referring to global symbols

I want to create a source file in which most of the functions there defined, are local to that source file. It's the same purpose that would be served in C by marking the functions static; in C++ one could also surround them with namespace { ... }. I get the impression in Lisp, the package system is the appropriate tool. However, my attempts so far are not working.
This is what I currently have, but SBCL rejects it with the claim that global-fun is undefined. Explicitly referring to it as cl-user:global-fun, produces similar results. What should I be doing?
(defun global-fun ()
(format t "global~%"))
(defpackage :local-package
(:use :common-lisp)
(:use :cl-user))
(in-package :local-package)
(defun local-fun ()
(global-fun)
(format t "local~%"))
You're nearly there. You might use Slime's autocompletion to find out.
Either export global-fun, or access it with a double colon: (cl-user::global-fun).
With another global-package:
(defpackage :global-package
(:use :common-lisp) ;; <-- can be :cl
;; (:use :cl-user) <-- not necessary
(:export :global-fun))
(in-package :global-package)
(defun global-fun () …)
(defpackage :local-package
(:use :cl
:global-defun)) ;; <-- one ":use" is possible
(in-package :local-package)
; etc
There seem to be some misconceptions here.
There is no such thing as a “global function” in Common Lisp. The thing you defined first in your file, global-fun is in some package, most likely the cl-user package.
There is also no direct correspondence between packages and files. You can define things for different packages in a single file, and you can define things for a single package in multiple files. To make things unambiguous and easy to read, there is a very sensible convention to always start a source file with an in-package form (in some styles preceded by a defpackage form), and to never put another in-package somewhere later in the file.
When you write a symbol without package, e. g. somefun or myarray, it is interned (i. e. a sort of idempotent registration) into the current package (see below what that is). This is independent from whether you currently define something or refer to it, because it is done by the reader when reading your source code forms. In both of the following forms, the symbol named foo is interned into the current package (and both result in the identical symbol to be used):
(defun foo ()
…)
(foo)
In order to refer to a symbol from a different package, you need to put the package name as a prefix with :: as separator, as in my-package::foo, but this is usually a code smell because…
… you should export any symbols that a user of your package is intended to use, from your package definition:
(defpackage my-package
(:use common-lisp)
(:export foo))
You can refer to exported symbols from another package with a single colon as separator, as in my-package:foo, and this is good style.
Now, the current package is just the value of the variable *package*. If you look at it from the point of view of a REPL session, this is the argument of the most recent in-package call. In the context of whole file compilation, it is the value of the lexically closest preceding in-package form. In the context of single-form compilation in a file, the IDE will (in any case I have seen) look for that preceding in-package form even if it is not evaluated explicitly. In a pristine Lisp image, the starting package is common-lisp-user, which has a nickname cl-user.

What's the meaning of "#+" in the code of cl-mysql? [duplicate]

This question already has answers here:
operator #+ and #- in .sbclrc
(2 answers)
Closed 6 years ago.
Recently I tried to read code about cl-mysql, but got stuck with the #+.
Tried to google it, but not work, so turn to here
(defun make-lock (name)
#+sb-thread (sb-thread:make-mutex :name name)
#+ecl (mp:make-lock :name name)
#+armedbear (ext:make-thread-lock)
#+ (and clisp mt) (mt:make-mutex :name name)
#+allegro (mp:make-process-lock :name name))
And looks like it is for different backend lisp compiler. But still no idea why write something like this.
Anyone can help me make it clear, thx.
#+ is a reader-macro that checks if a keyword is in the special variable *FEATURES*. If it isn't there, the following form will be skipped over (by the reader; the compiler will never see it). There is also #- which does the opposite.
There are some things that aren't part of the Common Lisp standard, but are important enough that all (or most) implementations provide a non-standard extension for them. When you want to use them in code that needs to work on multiple implementations, you have to use read-time conditionals to provide the correct code for the current implementation. Mutexes (and threads in general) are one of those things.
Of course there may be features provided by third party libraries as well. The contents of *FEATURES* will look something like this:
(:SWANK :QUICKLISP :SB-BSD-SOCKETS-ADDRINFO :ASDF-PACKAGE-SYSTEM :ASDF3.1
:ASDF3 :ASDF2 :ASDF :OS-UNIX :NON-BASE-CHARS-EXIST-P :ASDF-UNICODE :64-BIT
:64-BIT-REGISTERS :ALIEN-CALLBACKS :ANSI-CL :ASH-RIGHT-VOPS
:C-STACK-IS-CONTROL-STACK :COMMON-LISP :COMPARE-AND-SWAP-VOPS
:COMPLEX-FLOAT-VOPS :CYCLE-COUNTER :ELF :FLOAT-EQL-VOPS
:FP-AND-PC-STANDARD-SAVE :GENCGC :IEEE-FLOATING-POINT :INLINE-CONSTANTS
:INTEGER-EQL-VOP :INTERLEAVED-RAW-SLOTS :LARGEFILE :LINKAGE-TABLE :LINUX
:LITTLE-ENDIAN :MEMORY-BARRIER-VOPS :MULTIPLY-HIGH-VOPS :OS-PROVIDES-DLADDR
:OS-PROVIDES-DLOPEN :OS-PROVIDES-GETPROTOBY-R :OS-PROVIDES-POLL
:OS-PROVIDES-PUTWC :OS-PROVIDES-SUSECONDS-T :PACKAGE-LOCAL-NICKNAMES
:PRECISE-ARG-COUNT-ERROR :RAW-INSTANCE-INIT-VOPS :SB-DOC :SB-EVAL :SB-FUTEX
:SB-LDB :SB-PACKAGE-LOCKS :SB-SIMD-PACK :SB-SOURCE-LOCATIONS :SB-TEST
:SB-THREAD :SB-UNICODE :SBCL :STACK-ALLOCATABLE-CLOSURES
:STACK-ALLOCATABLE-FIXED-OBJECTS :STACK-ALLOCATABLE-LISTS
:STACK-ALLOCATABLE-VECTORS :STACK-GROWS-DOWNWARD-NOT-UPWARD :SYMBOL-INFO-VOPS
:UNIX :UNWIND-TO-FRAME-AND-CALL-VOP :X86-64)
So if you wanted to write code that depends on Quicklisp for example, you could use #+quicklisp. If you wanted code that is only run if Quicklisp is not available, you'd use #-quicklisp.
You can also use a boolean expression of features. For example,
#+(or sbcl ecl) (format t "Foo!")
would print Foo! on either SBCL or ECL.
#+(and sbcl quicklisp) (format t "Bar!")
would only print Bar! on SBCL that has Quicklisp available.
One could imagine that we can write:
(defun make-lock (name)
(cond ((member :sb-thread *features)
(sb-thread:make-mutex :name name))
((member :ecl *features*)
(mp:make-lock :name name))
...))
But that does usually not work, because we can't read symbols when their package is not existing and some packages are implementation/library/application specific. Packages are not created at read time in a lazy/automatic fashion.
In Common Lisp, reading a symbol of a package, which does not exist, leads to an error:
CL-USER 1 > (read-from-string "foo:bar")
Error: Reader cannot find package FOO.
1 (continue) Create the FOO package.
2 Use another package instead of FOO.
3 Try finding package FOO again.
4 (abort) Return to level 0.
5 Return to top loop level 0.
In your example sb-thread:make-mutex is a symbol which makes sense in SBCL, but not in Allegro CL. Additionally the package SB-THREAD does not exist in Allegro CL. Thus Allegro CL needs to be protected from reading it. In this case, the symbol sb-thread:make-mutex will only be read, if the the feature sb-thread is present on the cl:*features* list. Which is likely only for SBCL, or a Lisp which claims to have sb-threads available.
The feature expressions here prevents the Lisp from trying to read symbols with unknown packages - the packages are unknown, because the respective software is not loaded or not available.

lexical binding lost when switching package

All I wanted was to load an initialisation file for swank which wouldn't affect my lisp when it's started without swank...
I first tried #+swank (defun...) in my file that's loaded from ccl-init (trying this on ccl 1.10 + windows), and soon realised it's sourced before swank is loaded (obviously).
My aim is to define a simple function in :cl-user everytime I start swank. I just ended up with a swank add-hook to load my init.lisp file, and since I want to define the function in cl-user, I tried this in the init.lisp:
(let ((current-package *package*))
(in-package :cl-user)
(defun cd (dir)
(swank:set-default-directory
(parse-namestring dir)))
(in-package current-package))
Now, I don't recall if a defun in let was allowed, but lisp doesn't complain for it, but rather tells me that cur-pck symbol doesn't exist, and it seems when we switch the package, cur-pck binding gets out of scope. I thought cur-pck is a lexical binding, and that it should be reachable from within the lexical region, being independent from a package, am I wrong?
Why do I switch packages? I'm thinking that loading this file from swank at some initialisation point will define things in some swank package, that's why I wanted to try switching to cl-user first, define the function symbol, and switch back to let swank do it's thing.
At this point I guess I need someone to tell me I'm approaching the problem from the wrong angle, and that I should better choose an easier solution.
Additionally, out of curiosity in case above is the complete wrong approach, is there a way to define a symbol in another package within a function or a closure?
Switching packages in a form has no direct effect on the form
Let's look at this:
(in-package "FOO")
(let ((x 10))
(in-package "BAR")
(setf x 20))
Which x does it set to 20? FOO::X or BAR::X?
Well, it is FOO::X. Switching packages during execution has no effect on the symbols already read. The whole let form is read at once and the *package* value is used for that. Having an IN-PACKAGE in the form itself has no effect on the form itself.
Symbol with a package prefix
If you want to use a symbol in a certain package, just write the package prefix:
cl-user:foo ; if FOO is exported and the package exists
or
cl-user::foo ; if foo is not exported and the package exists
for example:
(defun cl-user::cd (...) ...)
Computing with symbols
You can also compute new symbols in packages you don't know yet:
(let ((sym-name "A-NEW-SYMBOL")
(my-package-name "SOME-EXISTING-PACKAGE"))
(intern sym-name my-package-name))
If the package does not exist, you can create it.
You can also set the function of a computed symbol:
(setf (symbol-function (compute-a-function-symbol))
#'(lambda ()
'foo))
If you want to define a function in a different package that the current one you can use a qualified symbol for a name
(defun cl-user::cd (dir)
(swank:set-default-directory
(parse-namestring dir)))
The binding is not being "lost". To test so yourself add (princ cur-pck) before the in-package form.
If you try evaluating (in-package *package*) you will see why your code fails to switch packages. The in-package macro does not evaluate its argument. The code that would give us the code we would want to evaluate is:
(let ((cur-pck *package*))
(in-package :cl-user)
(defun cd (dir)
(swank:set-default-directory
(1+ 2)))
(princ cur-pck)
`(in-package ,cur-pck))
However, as Rainer Joswig noted in his answer the in-package has no effect on forms already read, so it wouldn't work as desired even as a macro.
A style nitpick, don't use abbreviations, write current-package.
IN-PACKAGE is a macro, not a function. The problem in your code is that saying (in-package cur-pck) tries not to switch into the package denoted by the cur-pck variable but to the package named CUR-PCK (which obviously does not exist).
You can set the package temporarily with
(let ((*package* (find-package :cl-user)))
(defun cd (dir)
...))
But then again, the easiest way to achieve what you are doing would be
(defun cl-user::cd (dir)
...)
which totally eliminates the need to set the current package.

Refer to symbol in another package not known at compile time in common-lisp

Is there a way to easily refer symbols in another other package without knowing it in advace ?
Let's say that I have a function like the following in a package names MY-PACKAGE
(defun foo-bar (foo bar)
`((,foo . foo)
(,bar . bar)))
If I call the above from the same package I'll get something like the following:
MY-PACKAGE> (foo-bar 1 2)
((FOO . 1) (BAR . 2))
If I call it from some other package, let's say CL-USER, the symbol returned refer to the package MY-PACKAGE:
CL-USER> (my-package:foo-bar 1 2)
((MY-PACKAGE:FOO . 1) (MY-PACKAGE:BAR . 2))
Sometimes, expecially when writing macros, I'd like to have the function return symbol interned in the package from which the function has been called (in this case CL-USER).
The only way I have been able to do this is by rewriting foo-bar as follows
(defun foo-bar (foo bar)
`((,(intern "FOO" *package*) . ,foo)
(,(intern "BAR" *package*) . ,bar)))
This gets ugly very soon, expecially when the symbols are given as parameters.
Is there any better way to handle this ?
Functions are not called from a package. Packages are only used by the reader and by symbol creating functions like INTERN. At call time the symbols of a function are already interned in the package where the source code was originally read. For the function itself is does not matter how you get it's symbol name and call it.
If you want to create symbols in different packages based on, say, the value of the variable *package*, then you have to say so. INTERN is the way to create new symbols and the package is a parameter. It is also possible to create symbols without interning them in a package.
If the package for the symbol does not matter, then one might want to use uninterned symbols or, typically, keyword symbols. Keyword symbols are interned in the package keyword and evaluate to themselves.
Using INTERN with *package* is fine if you really intend to intern the key symbol of the association list in a different package depending on the context. However, note that *package* may not be bound to the package of the call unless you bind it explicitly. You can resolve that by defining a macro instead of a function and use the *package* binding at macro expansion time.
If the symbols are given as parameters to the function call, they are likely already interned in the package of the function call. Hence there is no need to use INTERN.
In case you are open to alternative approaches, Rainer's answer provides good suggestions such as using keyword symbols like :foo and :bar instead.

Resources